- Fixed VS2012 build issues and crashes on Windows 8 x64 - Added a VS2012 solution to build libjack as a static lib for use with Visual Studio 2012 projects - removed unnecessary/outdated binary files that cause crashes and problems on Win 8pull/36/head
| @@ -1943,7 +1943,7 @@ LIB_EXPORT char *jack_client_get_uuid(jack_client_t* ext_client) | |||
| } else { | |||
| char retval[16]; | |||
| snprintf(retval, sizeof(retval), "%d", client->GetClientControl()->fSessionID); | |||
| return strdup(retval); | |||
| return _strdup(retval); | |||
| } | |||
| } | |||
| @@ -308,11 +308,11 @@ int JackClient::ClientNotify(int refnum, const char* name, int notify, int sync, | |||
| jack_session_event_t* event = (jack_session_event_t*)malloc( sizeof(jack_session_event_t)); | |||
| char uuid_buf[JACK_UUID_SIZE]; | |||
| event->type = (jack_session_event_type_t)value1; | |||
| event->session_dir = strdup(message); | |||
| event->session_dir = _strdup(message); | |||
| event->command_line = NULL; | |||
| event->flags = (jack_session_flags_t)0; | |||
| snprintf(uuid_buf, sizeof(uuid_buf), "%d", GetClientControl()->fSessionID); | |||
| event->client_uuid = strdup(uuid_buf); | |||
| event->client_uuid = _strdup(uuid_buf); | |||
| fSessionReply = kPendingSessionReply; | |||
| // Session callback may change fSessionReply by directly using jack_session_reply | |||
| fSession(event, fSessionArg); | |||
| @@ -1199,7 +1199,7 @@ char* JackClient::GetInternalClientName(int ref) | |||
| char name_res[JACK_CLIENT_NAME_SIZE + 1]; | |||
| int result = -1; | |||
| fChannel->GetInternalClientName(GetClientControl()->fRefNum, ref, name_res, &result); | |||
| return (result < 0) ? NULL : strdup(name_res); | |||
| return (result < 0) ? NULL : _strdup(name_res); | |||
| } | |||
| int JackClient::InternalClientHandle(const char* client_name, jack_status_t* status) | |||
| @@ -1288,7 +1288,7 @@ char* JackClient::GetUUIDForClientName(const char* client_name) | |||
| char uuid_res[JACK_UUID_SIZE]; | |||
| int result = -1; | |||
| fChannel->GetUUIDForClientName(GetClientControl()->fRefNum, client_name, uuid_res, &result); | |||
| return (result) ? NULL : strdup(uuid_res); | |||
| return (result) ? NULL : _strdup(uuid_res); | |||
| } | |||
| char* JackClient::GetClientNameByUUID(const char* uuid) | |||
| @@ -1296,7 +1296,7 @@ char* JackClient::GetClientNameByUUID(const char* uuid) | |||
| char name_res[JACK_CLIENT_NAME_SIZE + 1]; | |||
| int result = -1; | |||
| fChannel->GetClientNameForUUID(GetClientControl()->fRefNum, uuid, name_res, &result); | |||
| return (result) ? NULL : strdup(name_res); | |||
| return (result) ? NULL : _strdup(name_res); | |||
| } | |||
| int JackClient::ReserveClientName(const char* client_name, const char* uuid) | |||
| @@ -1283,9 +1283,9 @@ struct JackSessionNotifyResult : public JackResult | |||
| int i = 0; | |||
| for (std::list<JackSessionCommand>::iterator ci = fCommandList.begin(); ci != fCommandList.end(); ci++) { | |||
| session_command[i].uuid = strdup(ci->fUUID); | |||
| session_command[i].client_name = strdup(ci->fClientName); | |||
| session_command[i].command = strdup(ci->fCommand); | |||
| session_command[i].uuid = _strdup(ci->fUUID); | |||
| session_command[i].client_name = _strdup(ci->fClientName); | |||
| session_command[i].command = _strdup(ci->fCommand); | |||
| session_command[i].flags = ci->fFlags; | |||
| i += 1; | |||
| } | |||
| @@ -63,18 +63,23 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
| #include <windows.h> | |||
| #ifdef _MSC_VER /* Microsoft compiler */ | |||
| #define __inline__ inline | |||
| #if (!defined(int8_t) && !defined(_STDINT_H)) | |||
| #define __int8_t_defined | |||
| typedef char int8_t; | |||
| typedef unsigned char uint8_t; | |||
| typedef short int16_t; | |||
| typedef unsigned short uint16_t; | |||
| typedef long int32_t; | |||
| typedef unsigned long uint32_t; | |||
| typedef LONGLONG int64_t; | |||
| typedef ULONGLONG uint64_t; | |||
| #endif | |||
| #if _MSC_VER >= 1700 | |||
| #include <stdint.h> | |||
| #define __inline__ inline | |||
| #else | |||
| #define __inline__ inline | |||
| #if (!defined(int8_t) && !defined(_STDINT_H)) | |||
| #define __int8_t_defined | |||
| typedef char int8_t; | |||
| typedef unsigned char uint8_t; | |||
| typedef short int16_t; | |||
| typedef unsigned short uint16_t; | |||
| typedef long int32_t; | |||
| typedef unsigned long uint32_t; | |||
| typedef LONGLONG int64_t; | |||
| typedef ULONGLONG uint64_t; | |||
| #endif | |||
| #endif | |||
| #elif __MINGW32__ /* MINGW */ | |||
| #include <stdint.h> | |||
| #include <sys/types.h> | |||
| @@ -18,59 +18,69 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. | |||
| */ | |||
| #ifndef __JackAtomic_WIN32__ | |||
| #define __JackAtomic_WIN32__ | |||
| #define __JackAtmic_WIN32__ | |||
| #include "JackTypes.h" | |||
| #ifndef __MINGW32__ | |||
| #ifdef __SMP__ | |||
| # define LOCK lock | |||
| #else | |||
| # define LOCK | |||
| #endif | |||
| #ifndef inline | |||
| #define inline __inline | |||
| #endif | |||
| //---------------------------------------------------------------- | |||
| // CAS functions | |||
| //---------------------------------------------------------------- | |||
| inline char CAS(volatile UInt32 value, UInt32 newvalue, volatile void * addr) | |||
| { | |||
| register char c; | |||
| __asm { | |||
| push ebx | |||
| push esi | |||
| mov esi, addr | |||
| mov eax, value | |||
| mov ebx, newvalue | |||
| LOCK cmpxchg dword ptr [esi], ebx | |||
| sete c | |||
| pop esi | |||
| pop ebx | |||
| } | |||
| return c; | |||
| } | |||
| #ifndef _WIN64 | |||
| #else | |||
| #ifndef __MINGW32__ | |||
| #ifdef __SMP__ | |||
| # define LOCK lock | |||
| #else | |||
| # define LOCK | |||
| #endif | |||
| #if _MSC_VER <= 1600 | |||
| #ifndef inline | |||
| #define inline __inline | |||
| #endif | |||
| #endif | |||
| #define LOCK "lock ; " | |||
| //---------------------------------------------------------------- | |||
| // CAS functions | |||
| //---------------------------------------------------------------- | |||
| inline char CAS(volatile UInt32 value, UInt32 newvalue, volatile void * addr) | |||
| { | |||
| register char c; | |||
| __asm { | |||
| push ebx | |||
| push esi | |||
| mov esi, addr | |||
| mov eax, value | |||
| mov ebx, newvalue | |||
| LOCK cmpxchg dword ptr [esi], ebx | |||
| sete c | |||
| pop esi | |||
| pop ebx | |||
| } | |||
| return c; | |||
| } | |||
| static inline char CAS(volatile UInt32 value, UInt32 newvalue, volatile void* addr) | |||
| { | |||
| register char ret; | |||
| __asm__ __volatile__ ( | |||
| "# CAS \n\t" | |||
| LOCK "cmpxchg %2, (%1) \n\t" | |||
| "sete %0 \n\t" | |||
| : "=a" (ret) | |||
| : "c" (addr), "d" (newvalue), "a" (value) | |||
| ); | |||
| return ret; | |||
| } | |||
| #else | |||
| #endif | |||
| #define LOCK "lock ; " | |||
| static inline char CAS(volatile UInt32 value, UInt32 newvalue, volatile void* addr) | |||
| { | |||
| register char ret; | |||
| __asm__ __volatile__ ( | |||
| "# CAS \n\t" | |||
| LOCK "cmpxchg %2, (%1) \n\t" | |||
| "sete %0 \n\t" | |||
| : "=a" (ret) | |||
| : "c" (addr), "d" (newvalue), "a" (value) | |||
| ); | |||
| return ret; | |||
| } | |||
| #endif | |||
| #else | |||
| static inline char CAS(volatile UInt32 value, UInt32 newvalue, volatile void* addr) | |||
| { | |||
| return InterlockedCompareExchange((UInt32*)addr, value, newvalue); | |||
| } | |||
| #endif // _WIN64 | |||
| #endif | |||
| #endif //__JackAtmic_WIN32__ | |||
| @@ -21,7 +21,11 @@ | |||
| #ifndef __JackCompilerDeps_WIN32__ | |||
| #define __JackCompilerDeps_WIN32__ | |||
| #define LIB_EXPORT __declspec(dllexport) | |||
| #ifndef JACKLIB_STATIC | |||
| #define LIB_EXPORT __declspec(dllexport) | |||
| #else | |||
| #define LIB_EXPORT | |||
| #endif | |||
| #ifdef SERVER_SIDE | |||
| #define SERVER_EXPORT __declspec(dllexport) | |||
| @@ -42,7 +46,7 @@ | |||
| #if defined(_MSC_VER) /* Added by JE - 31-01-2012 */ | |||
| #define vsnprintf _vsnprintf | |||
| #define snprintf _snprintf | |||
| #define strdup _strdup | |||
| //#define strdup _strdup | |||
| #endif | |||
| #endif | |||
| @@ -27,7 +27,9 @@ | |||
| #define PATH_MAX 512 | |||
| #endif | |||
| #define UINT32_MAX 4294967295U | |||
| #if _MSC_VER <= 1600 | |||
| #define UINT32_MAX 4294967295U | |||
| #endif | |||
| #define DRIVER_HANDLE HINSTANCE | |||
| #define LoadDriverModule(name) LoadLibrary((name)) | |||
| @@ -155,7 +155,7 @@ error: | |||
| // Close the pipes, server wont be able to create them otherwise. | |||
| fNotificationListenPipe.Close(); | |||
| fRequest->Close(); | |||
| fClient->ShutDown(JACK_SERVER_FAILURE); | |||
| fClient->ShutDown(JackStatus::JackServerError, JACK_SERVER_FAILURE); | |||
| return false; | |||
| } | |||
| @@ -0,0 +1,9 @@ | |||
| <?xml version="1.0" encoding="UTF-8" standalone="yes" ?> | |||
| <CodeBlocks_layout_file> | |||
| <ActiveTarget name="Win32 Release 64bits" /> | |||
| <File name="libjack.rc" open="1" top="1" tabpos="1" split="0" active="1" splitpos="0" zoom_1="0" zoom_2="0"> | |||
| <Cursor> | |||
| <Cursor1 position="998" topLine="0" /> | |||
| </Cursor> | |||
| </File> | |||
| </CodeBlocks_layout_file> | |||
| @@ -3,7 +3,7 @@ | |||
| // http://www.resedit.net | |||
| #include "resource.h" | |||
| #include "afxres.h" | |||
| #include "WinResrc.h" | |||
| // | |||
| @@ -0,0 +1,39 @@ | |||
| | |||
| Microsoft Visual Studio Solution File, Format Version 12.00 | |||
| # Visual Studio Express 2012 for Windows Desktop | |||
| Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libjack", "libjack.vcxproj", "{E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}" | |||
| ProjectSection(ProjectDependencies) = postProject | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8} = {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8} | |||
| EndProjectSection | |||
| EndProject | |||
| Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tre", "..\tre-0.8.0\win32\tre.vcxproj", "{E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}" | |||
| EndProject | |||
| Global | |||
| GlobalSection(SolutionConfigurationPlatforms) = preSolution | |||
| Debug|Win32 = Debug|Win32 | |||
| Debug|x64 = Debug|x64 | |||
| Release|Win32 = Release|Win32 | |||
| Release|x64 = Release|x64 | |||
| EndGlobalSection | |||
| GlobalSection(ProjectConfigurationPlatforms) = postSolution | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Debug|Win32.ActiveCfg = Debug|Win32 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Debug|Win32.Build.0 = Debug|Win32 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Debug|x64.ActiveCfg = Debug|x64 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Debug|x64.Build.0 = Debug|x64 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Release|Win32.ActiveCfg = Release|Win32 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Release|Win32.Build.0 = Release|Win32 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Release|x64.ActiveCfg = Release|x64 | |||
| {E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}.Release|x64.Build.0 = Release|x64 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Debug|Win32.ActiveCfg = Debug|Win32 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Debug|Win32.Build.0 = Debug|Win32 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Debug|x64.ActiveCfg = Debug|x64 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Debug|x64.Build.0 = Debug|x64 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Release|Win32.ActiveCfg = Release|Win32 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Release|Win32.Build.0 = Release|Win32 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Release|x64.ActiveCfg = Release|x64 | |||
| {E7109D7C-58A9-4D56-A2A4-3538A4ED2DB8}.Release|x64.Build.0 = Release|x64 | |||
| EndGlobalSection | |||
| GlobalSection(SolutionProperties) = preSolution | |||
| HideSolutionNode = FALSE | |||
| EndGlobalSection | |||
| EndGlobal | |||
| @@ -0,0 +1,235 @@ | |||
| <?xml version="1.0" encoding="utf-8"?> | |||
| <Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> | |||
| <ItemGroup Label="ProjectConfigurations"> | |||
| <ProjectConfiguration Include="Debug|Win32"> | |||
| <Configuration>Debug</Configuration> | |||
| <Platform>Win32</Platform> | |||
| </ProjectConfiguration> | |||
| <ProjectConfiguration Include="Debug|x64"> | |||
| <Configuration>Debug</Configuration> | |||
| <Platform>x64</Platform> | |||
| </ProjectConfiguration> | |||
| <ProjectConfiguration Include="Release|Win32"> | |||
| <Configuration>Release</Configuration> | |||
| <Platform>Win32</Platform> | |||
| </ProjectConfiguration> | |||
| <ProjectConfiguration Include="Release|x64"> | |||
| <Configuration>Release</Configuration> | |||
| <Platform>x64</Platform> | |||
| </ProjectConfiguration> | |||
| </ItemGroup> | |||
| <PropertyGroup Label="Globals"> | |||
| <ProjectGuid>{E0BBC11B-6FE1-4DCE-AC72-12950181CA2D}</ProjectGuid> | |||
| <RootNamespace>libjack</RootNamespace> | |||
| </PropertyGroup> | |||
| <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" /> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration"> | |||
| <ConfigurationType>StaticLibrary</ConfigurationType> | |||
| <UseDebugLibraries>true</UseDebugLibraries> | |||
| <PlatformToolset>v110_xp</PlatformToolset> | |||
| <CharacterSet>MultiByte</CharacterSet> | |||
| </PropertyGroup> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration"> | |||
| <ConfigurationType>StaticLibrary</ConfigurationType> | |||
| <UseDebugLibraries>true</UseDebugLibraries> | |||
| <PlatformToolset>v110</PlatformToolset> | |||
| <CharacterSet>MultiByte</CharacterSet> | |||
| </PropertyGroup> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration"> | |||
| <ConfigurationType>StaticLibrary</ConfigurationType> | |||
| <UseDebugLibraries>false</UseDebugLibraries> | |||
| <PlatformToolset>v110_xp</PlatformToolset> | |||
| <WholeProgramOptimization>true</WholeProgramOptimization> | |||
| <CharacterSet>MultiByte</CharacterSet> | |||
| </PropertyGroup> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration"> | |||
| <ConfigurationType>StaticLibrary</ConfigurationType> | |||
| <UseDebugLibraries>false</UseDebugLibraries> | |||
| <PlatformToolset>v110</PlatformToolset> | |||
| <WholeProgramOptimization>true</WholeProgramOptimization> | |||
| <CharacterSet>MultiByte</CharacterSet> | |||
| </PropertyGroup> | |||
| <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" /> | |||
| <ImportGroup Label="ExtensionSettings"> | |||
| </ImportGroup> | |||
| <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> | |||
| <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> | |||
| </ImportGroup> | |||
| <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets"> | |||
| <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> | |||
| </ImportGroup> | |||
| <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> | |||
| <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> | |||
| </ImportGroup> | |||
| <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets"> | |||
| <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> | |||
| </ImportGroup> | |||
| <PropertyGroup Label="UserMacros" /> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> | |||
| <TargetName>$(ProjectName)_d</TargetName> | |||
| </PropertyGroup> | |||
| <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> | |||
| <TargetName>$(ProjectName)_d</TargetName> | |||
| </PropertyGroup> | |||
| <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> | |||
| <ClCompile> | |||
| <WarningLevel>Level3</WarningLevel> | |||
| <Optimization>Disabled</Optimization> | |||
| <SDLCheck>true</SDLCheck> | |||
| <AdditionalIncludeDirectories>..\tre-0.8.0\win32;..\tre-0.8.0\lib;..\..\common\jack;..\;..\..\common</AdditionalIncludeDirectories> | |||
| <PreprocessorDefinitions>JACKLIB_STATIC;DEBUG;_CRT_SECURE_NO_WARNINGS;WIN32;__SMP__;STDC_HEADERS;_WINDOWS;_MBCS;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||
| <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary> | |||
| <InlineFunctionExpansion>Disabled</InlineFunctionExpansion> | |||
| <ProgramDataBaseFileName>$(IntDir)$(ProjectName)_$(PlatformToolsetVersion).pdb</ProgramDataBaseFileName> | |||
| </ClCompile> | |||
| <Link> | |||
| <GenerateDebugInformation>true</GenerateDebugInformation> | |||
| </Link> | |||
| <Lib> | |||
| <AdditionalDependencies>tre.lib</AdditionalDependencies> | |||
| </Lib> | |||
| <Lib> | |||
| <AdditionalLibraryDirectories>..\tre-0.8.0\win32\$(Configuration)</AdditionalLibraryDirectories> | |||
| <TargetMachine>MachineX86</TargetMachine> | |||
| </Lib> | |||
| <ProjectReference> | |||
| <LinkLibraryDependencies>true</LinkLibraryDependencies> | |||
| </ProjectReference> | |||
| </ItemDefinitionGroup> | |||
| <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> | |||
| <ClCompile> | |||
| <WarningLevel>Level3</WarningLevel> | |||
| <Optimization>Disabled</Optimization> | |||
| <SDLCheck>true</SDLCheck> | |||
| <AdditionalIncludeDirectories>..\tre-0.8.0\win32;..\tre-0.8.0\lib;..\..\common\jack;..\;..\..\common</AdditionalIncludeDirectories> | |||
| <PreprocessorDefinitions>JACKLIB_STATIC;DEBUG;_CRT_SECURE_NO_WARNINGS;WIN32;__SMP__;STDC_HEADERS;_WINDOWS;_MBCS;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||
| <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary> | |||
| <InlineFunctionExpansion>Disabled</InlineFunctionExpansion> | |||
| <ProgramDataBaseFileName>$(IntDir)$(ProjectName)_$(PlatformToolsetVersion).pdb</ProgramDataBaseFileName> | |||
| <DebugInformationFormat>EditAndContinue</DebugInformationFormat> | |||
| </ClCompile> | |||
| <Link> | |||
| <GenerateDebugInformation>true</GenerateDebugInformation> | |||
| </Link> | |||
| <Lib> | |||
| <AdditionalDependencies>tre.lib</AdditionalDependencies> | |||
| </Lib> | |||
| <Lib> | |||
| <AdditionalLibraryDirectories>x64\$(Configuration)</AdditionalLibraryDirectories> | |||
| </Lib> | |||
| <ProjectReference> | |||
| <LinkLibraryDependencies>true</LinkLibraryDependencies> | |||
| </ProjectReference> | |||
| </ItemDefinitionGroup> | |||
| <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> | |||
| <ClCompile> | |||
| <WarningLevel>Level3</WarningLevel> | |||
| <Optimization>MaxSpeed</Optimization> | |||
| <FunctionLevelLinking>true</FunctionLevelLinking> | |||
| <IntrinsicFunctions>true</IntrinsicFunctions> | |||
| <SDLCheck>true</SDLCheck> | |||
| <RuntimeLibrary>MultiThreaded</RuntimeLibrary> | |||
| <PreprocessorDefinitions>JACKLIB_STATIC;NDEBUG;_CRT_SECURE_NO_WARNINGS;WIN32;__SMP__;STDC_HEADERS;_WINDOWS;_MBCS;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||
| <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion> | |||
| <WholeProgramOptimization>false</WholeProgramOptimization> | |||
| <AdditionalIncludeDirectories>..\tre-0.8.0\win32;..\tre-0.8.0\lib;..\..\common\jack;..\;..\..\common</AdditionalIncludeDirectories> | |||
| </ClCompile> | |||
| <Link> | |||
| <GenerateDebugInformation>true</GenerateDebugInformation> | |||
| <EnableCOMDATFolding>true</EnableCOMDATFolding> | |||
| <OptimizeReferences>true</OptimizeReferences> | |||
| </Link> | |||
| <Lib> | |||
| <AdditionalLibraryDirectories>..\tre-0.8.0\win32\$(Configuration)</AdditionalLibraryDirectories> | |||
| <AdditionalDependencies>tre.lib</AdditionalDependencies> | |||
| <TargetMachine>MachineX86</TargetMachine> | |||
| <LinkTimeCodeGeneration>true</LinkTimeCodeGeneration> | |||
| </Lib> | |||
| <ProjectReference> | |||
| <LinkLibraryDependencies>true</LinkLibraryDependencies> | |||
| </ProjectReference> | |||
| </ItemDefinitionGroup> | |||
| <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> | |||
| <ClCompile> | |||
| <WarningLevel>Level3</WarningLevel> | |||
| <Optimization>MaxSpeed</Optimization> | |||
| <FunctionLevelLinking>true</FunctionLevelLinking> | |||
| <IntrinsicFunctions>true</IntrinsicFunctions> | |||
| <SDLCheck>true</SDLCheck> | |||
| <RuntimeLibrary>MultiThreaded</RuntimeLibrary> | |||
| <PreprocessorDefinitions>JACKLIB_STATIC;NDEBUG;_CRT_SECURE_NO_WARNINGS;WIN32;__SMP__;STDC_HEADERS;_WINDOWS;_MBCS;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||
| <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion> | |||
| <WholeProgramOptimization>false</WholeProgramOptimization> | |||
| <AdditionalIncludeDirectories>..\tre-0.8.0\win32;..\tre-0.8.0\lib;..\..\common\jack;..\;..\..\common</AdditionalIncludeDirectories> | |||
| </ClCompile> | |||
| <Link> | |||
| <GenerateDebugInformation>true</GenerateDebugInformation> | |||
| <EnableCOMDATFolding>true</EnableCOMDATFolding> | |||
| <OptimizeReferences>true</OptimizeReferences> | |||
| </Link> | |||
| <Lib> | |||
| <AdditionalLibraryDirectories>x64\$(Configuration)</AdditionalLibraryDirectories> | |||
| <AdditionalDependencies>tre.lib</AdditionalDependencies> | |||
| </Lib> | |||
| </ItemDefinitionGroup> | |||
| <ItemGroup> | |||
| <ClCompile Include="..\..\common\JackActivationCount.cpp" /> | |||
| <ClCompile Include="..\..\common\JackAPI.cpp" /> | |||
| <ClCompile Include="..\..\common\JackAudioPort.cpp" /> | |||
| <ClCompile Include="..\..\common\JackClient.cpp" /> | |||
| <ClCompile Include="..\..\common\JackConnectionManager.cpp" /> | |||
| <ClCompile Include="..\..\common\JackDebugClient.cpp" /> | |||
| <ClCompile Include="..\..\common\JackEngineControl.cpp" /> | |||
| <ClCompile Include="..\..\common\JackEngineProfiling.cpp" /> | |||
| <ClCompile Include="..\..\common\JackError.cpp" /> | |||
| <ClCompile Include="..\..\common\JackException.cpp" /> | |||
| <ClCompile Include="..\..\common\JackFrameTimer.cpp" /> | |||
| <ClCompile Include="..\..\common\JackGenericClientChannel.cpp" /> | |||
| <ClCompile Include="..\..\common\JackGlobals.cpp" /> | |||
| <ClCompile Include="..\..\common\JackGraphManager.cpp" /> | |||
| <ClCompile Include="..\..\common\JackLibAPI.cpp" /> | |||
| <ClCompile Include="..\..\common\JackLibClient.cpp" /> | |||
| <ClCompile Include="..\..\common\JackMessageBuffer.cpp" /> | |||
| <ClCompile Include="..\..\common\JackMidiAPI.cpp" /> | |||
| <ClCompile Include="..\..\common\JackMidiPort.cpp" /> | |||
| <ClCompile Include="..\..\common\JackPort.cpp" /> | |||
| <ClCompile Include="..\..\common\JackPortType.cpp" /> | |||
| <ClCompile Include="..\..\common\JackShmMem.cpp" /> | |||
| <ClCompile Include="..\..\common\JackTools.cpp" /> | |||
| <ClCompile Include="..\..\common\JackTransportEngine.cpp" /> | |||
| <ClCompile Include="..\..\common\ringbuffer.c" /> | |||
| <ClCompile Include="..\..\common\shm.c" /> | |||
| <ClCompile Include="..\JackMMCSS.cpp" /> | |||
| <ClCompile Include="..\JackWinMutex.cpp" /> | |||
| <ClCompile Include="..\JackWinNamedPipe.cpp" /> | |||
| <ClCompile Include="..\JackWinNamedPipeClientChannel.cpp" /> | |||
| <ClCompile Include="..\JackWinProcessSync.cpp" /> | |||
| <ClCompile Include="..\JackWinSemaphore.cpp" /> | |||
| <ClCompile Include="..\JackWinServerLaunch.cpp" /> | |||
| <ClCompile Include="..\JackWinThread.cpp" /> | |||
| <ClCompile Include="..\JackWinTime.c" /> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <ClInclude Include="..\..\common\jack\control.h" /> | |||
| <ClInclude Include="..\..\common\jack\intclient.h" /> | |||
| <ClInclude Include="..\..\common\jack\jack.h" /> | |||
| <ClInclude Include="..\..\common\jack\jslist.h" /> | |||
| <ClInclude Include="..\..\common\jack\midiport.h" /> | |||
| <ClInclude Include="..\..\common\jack\net.h" /> | |||
| <ClInclude Include="..\..\common\jack\ringbuffer.h" /> | |||
| <ClInclude Include="..\..\common\jack\session.h" /> | |||
| <ClInclude Include="..\..\common\jack\statistics.h" /> | |||
| <ClInclude Include="..\..\common\jack\systemdeps.h" /> | |||
| <ClInclude Include="..\..\common\jack\thread.h" /> | |||
| <ClInclude Include="..\..\common\jack\transport.h" /> | |||
| <ClInclude Include="..\..\common\jack\types.h" /> | |||
| <ClInclude Include="..\..\common\jack\weakjack.h" /> | |||
| <ClInclude Include="..\..\common\jack\weakmacros.h" /> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <ResourceCompile Include="..\libjack.rc" /> | |||
| </ItemGroup> | |||
| <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" /> | |||
| <ImportGroup Label="ExtensionTargets"> | |||
| </ImportGroup> | |||
| </Project> | |||
| @@ -0,0 +1,176 @@ | |||
| <?xml version="1.0" encoding="utf-8"?> | |||
| <Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> | |||
| <ItemGroup> | |||
| <Filter Include="Quelldateien"> | |||
| <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier> | |||
| <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions> | |||
| </Filter> | |||
| <Filter Include="Headerdateien"> | |||
| <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier> | |||
| <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions> | |||
| </Filter> | |||
| <Filter Include="Ressourcendateien"> | |||
| <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier> | |||
| <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions> | |||
| </Filter> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <ClCompile Include="..\..\common\JackActivationCount.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackAPI.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackAudioPort.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackClient.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackConnectionManager.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackDebugClient.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackEngineControl.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackEngineProfiling.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackError.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackException.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackFrameTimer.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackGenericClientChannel.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackGlobals.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackGraphManager.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackLibAPI.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackLibClient.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackMessageBuffer.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackMidiAPI.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackMidiPort.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackPort.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackPortType.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackShmMem.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackTools.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\JackTransportEngine.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\ringbuffer.c"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\..\common\shm.c"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackMMCSS.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinMutex.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinNamedPipe.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinNamedPipeClientChannel.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinProcessSync.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinSemaphore.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinServerLaunch.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinThread.cpp"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| <ClCompile Include="..\JackWinTime.c"> | |||
| <Filter>Quelldateien</Filter> | |||
| </ClCompile> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <ClInclude Include="..\..\common\jack\control.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\intclient.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\jack.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\jslist.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\midiport.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\net.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\ringbuffer.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\session.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\statistics.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\systemdeps.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\thread.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\transport.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\types.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\weakjack.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| <ClInclude Include="..\..\common\jack\weakmacros.h"> | |||
| <Filter>Headerdateien</Filter> | |||
| </ClInclude> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <ResourceCompile Include="..\libjack.rc"> | |||
| <Filter>Ressourcendateien</Filter> | |||
| </ResourceCompile> | |||
| </ItemGroup> | |||
| </Project> | |||
| @@ -0,0 +1 @@ | |||
| Ville Laurikari <vl@iki.fi> | |||
| @@ -0,0 +1,237 @@ | |||
| Installation Instructions | |||
| ************************* | |||
| Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002, 2004, 2005, | |||
| 2006, 2007 Free Software Foundation, Inc. | |||
| This file is free documentation; the Free Software Foundation gives | |||
| unlimited permission to copy, distribute and modify it. | |||
| Basic Installation | |||
| ================== | |||
| Briefly, the shell commands `./configure; make; make install' should | |||
| configure, build, and install this package. The following | |||
| more-detailed instructions are generic; see the `README' file for | |||
| instructions specific to this package. | |||
| The `configure' shell script attempts to guess correct values for | |||
| various system-dependent variables used during compilation. It uses | |||
| those values to create a `Makefile' in each directory of the package. | |||
| It may also create one or more `.h' files containing system-dependent | |||
| definitions. Finally, it creates a shell script `config.status' that | |||
| you can run in the future to recreate the current configuration, and a | |||
| file `config.log' containing compiler output (useful mainly for | |||
| debugging `configure'). | |||
| It can also use an optional file (typically called `config.cache' | |||
| and enabled with `--cache-file=config.cache' or simply `-C') that saves | |||
| the results of its tests to speed up reconfiguring. Caching is | |||
| disabled by default to prevent problems with accidental use of stale | |||
| cache files. | |||
| If you need to do unusual things to compile the package, please try | |||
| to figure out how `configure' could check whether to do them, and mail | |||
| diffs or instructions to the address given in the `README' so they can | |||
| be considered for the next release. If you are using the cache, and at | |||
| some point `config.cache' contains results you don't want to keep, you | |||
| may remove or edit it. | |||
| The file `configure.ac' (or `configure.in') is used to create | |||
| `configure' by a program called `autoconf'. You need `configure.ac' if | |||
| you want to change it or regenerate `configure' using a newer version | |||
| of `autoconf'. | |||
| The simplest way to compile this package is: | |||
| 1. `cd' to the directory containing the package's source code and type | |||
| `./configure' to configure the package for your system. | |||
| Running `configure' might take a while. While running, it prints | |||
| some messages telling which features it is checking for. | |||
| 2. Type `make' to compile the package. | |||
| 3. Optionally, type `make check' to run any self-tests that come with | |||
| the package. | |||
| 4. Type `make install' to install the programs and any data files and | |||
| documentation. | |||
| 5. You can remove the program binaries and object files from the | |||
| source code directory by typing `make clean'. To also remove the | |||
| files that `configure' created (so you can compile the package for | |||
| a different kind of computer), type `make distclean'. There is | |||
| also a `make maintainer-clean' target, but that is intended mainly | |||
| for the package's developers. If you use it, you may have to get | |||
| all sorts of other programs in order to regenerate files that came | |||
| with the distribution. | |||
| 6. Often, you can also type `make uninstall' to remove the installed | |||
| files again. | |||
| Compilers and Options | |||
| ===================== | |||
| Some systems require unusual options for compilation or linking that the | |||
| `configure' script does not know about. Run `./configure --help' for | |||
| details on some of the pertinent environment variables. | |||
| You can give `configure' initial values for configuration parameters | |||
| by setting variables in the command line or in the environment. Here | |||
| is an example: | |||
| ./configure CC=c99 CFLAGS=-g LIBS=-lposix | |||
| *Note Defining Variables::, for more details. | |||
| Compiling For Multiple Architectures | |||
| ==================================== | |||
| You can compile the package for more than one kind of computer at the | |||
| same time, by placing the object files for each architecture in their | |||
| own directory. To do this, you can use GNU `make'. `cd' to the | |||
| directory where you want the object files and executables to go and run | |||
| the `configure' script. `configure' automatically checks for the | |||
| source code in the directory that `configure' is in and in `..'. | |||
| With a non-GNU `make', it is safer to compile the package for one | |||
| architecture at a time in the source code directory. After you have | |||
| installed the package for one architecture, use `make distclean' before | |||
| reconfiguring for another architecture. | |||
| Installation Names | |||
| ================== | |||
| By default, `make install' installs the package's commands under | |||
| `/usr/local/bin', include files under `/usr/local/include', etc. You | |||
| can specify an installation prefix other than `/usr/local' by giving | |||
| `configure' the option `--prefix=PREFIX'. | |||
| You can specify separate installation prefixes for | |||
| architecture-specific files and architecture-independent files. If you | |||
| pass the option `--exec-prefix=PREFIX' to `configure', the package uses | |||
| PREFIX as the prefix for installing programs and libraries. | |||
| Documentation and other data files still use the regular prefix. | |||
| In addition, if you use an unusual directory layout you can give | |||
| options like `--bindir=DIR' to specify different values for particular | |||
| kinds of files. Run `configure --help' for a list of the directories | |||
| you can set and what kinds of files go in them. | |||
| If the package supports it, you can cause programs to be installed | |||
| with an extra prefix or suffix on their names by giving `configure' the | |||
| option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'. | |||
| Optional Features | |||
| ================= | |||
| Some packages pay attention to `--enable-FEATURE' options to | |||
| `configure', where FEATURE indicates an optional part of the package. | |||
| They may also pay attention to `--with-PACKAGE' options, where PACKAGE | |||
| is something like `gnu-as' or `x' (for the X Window System). The | |||
| `README' should mention any `--enable-' and `--with-' options that the | |||
| package recognizes. | |||
| For packages that use the X Window System, `configure' can usually | |||
| find the X include and library files automatically, but if it doesn't, | |||
| you can use the `configure' options `--x-includes=DIR' and | |||
| `--x-libraries=DIR' to specify their locations. | |||
| Specifying the System Type | |||
| ========================== | |||
| There may be some features `configure' cannot figure out automatically, | |||
| but needs to determine by the type of machine the package will run on. | |||
| Usually, assuming the package is built to be run on the _same_ | |||
| architectures, `configure' can figure that out, but if it prints a | |||
| message saying it cannot guess the machine type, give it the | |||
| `--build=TYPE' option. TYPE can either be a short name for the system | |||
| type, such as `sun4', or a canonical name which has the form: | |||
| CPU-COMPANY-SYSTEM | |||
| where SYSTEM can have one of these forms: | |||
| OS KERNEL-OS | |||
| See the file `config.sub' for the possible values of each field. If | |||
| `config.sub' isn't included in this package, then this package doesn't | |||
| need to know the machine type. | |||
| If you are _building_ compiler tools for cross-compiling, you should | |||
| use the option `--target=TYPE' to select the type of system they will | |||
| produce code for. | |||
| If you want to _use_ a cross compiler, that generates code for a | |||
| platform different from the build platform, you should specify the | |||
| "host" platform (i.e., that on which the generated programs will | |||
| eventually be run) with `--host=TYPE'. | |||
| Sharing Defaults | |||
| ================ | |||
| If you want to set default values for `configure' scripts to share, you | |||
| can create a site shell script called `config.site' that gives default | |||
| values for variables like `CC', `cache_file', and `prefix'. | |||
| `configure' looks for `PREFIX/share/config.site' if it exists, then | |||
| `PREFIX/etc/config.site' if it exists. Or, you can set the | |||
| `CONFIG_SITE' environment variable to the location of the site script. | |||
| A warning: not all `configure' scripts look for a site script. | |||
| Defining Variables | |||
| ================== | |||
| Variables not defined in a site shell script can be set in the | |||
| environment passed to `configure'. However, some packages may run | |||
| configure again during the build, and the customized values of these | |||
| variables may be lost. In order to avoid this problem, you should set | |||
| them in the `configure' command line, using `VAR=value'. For example: | |||
| ./configure CC=/usr/local2/bin/gcc | |||
| causes the specified `gcc' to be used as the C compiler (unless it is | |||
| overridden in the site shell script). | |||
| Unfortunately, this technique does not work for `CONFIG_SHELL' due to | |||
| an Autoconf bug. Until the bug is fixed you can use this workaround: | |||
| CONFIG_SHELL=/bin/bash /bin/bash ./configure CONFIG_SHELL=/bin/bash | |||
| `configure' Invocation | |||
| ====================== | |||
| `configure' recognizes the following options to control how it operates. | |||
| `--help' | |||
| `-h' | |||
| Print a summary of the options to `configure', and exit. | |||
| `--version' | |||
| `-V' | |||
| Print the version of Autoconf used to generate the `configure' | |||
| script, and exit. | |||
| `--cache-file=FILE' | |||
| Enable the cache: use and save the results of the tests in FILE, | |||
| traditionally `config.cache'. FILE defaults to `/dev/null' to | |||
| disable caching. | |||
| `--config-cache' | |||
| `-C' | |||
| Alias for `--cache-file=config.cache'. | |||
| `--quiet' | |||
| `--silent' | |||
| `-q' | |||
| Do not print messages saying which checks are being made. To | |||
| suppress all normal output, redirect it to `/dev/null' (any error | |||
| messages will still be shown). | |||
| `--srcdir=DIR' | |||
| Look for the package's source code in directory DIR. Usually | |||
| `configure' can determine that directory automatically. | |||
| `configure' also accepts some other, not widely useful, options. Run | |||
| `configure --help' for more details. | |||
| @@ -0,0 +1,29 @@ | |||
| This is the license, copyright notice, and disclaimer for TRE, a regex | |||
| matching package (library and tools) with support for approximate | |||
| matching. | |||
| Copyright (c) 2001-2009 Ville Laurikari <vl@iki.fi> | |||
| All rights reserved. | |||
| Redistribution and use in source and binary forms, with or without | |||
| modification, are permitted provided that the following conditions | |||
| are met: | |||
| 1. Redistributions of source code must retain the above copyright | |||
| notice, this list of conditions and the following disclaimer. | |||
| 2. Redistributions in binary form must reproduce the above copyright | |||
| notice, this list of conditions and the following disclaimer in the | |||
| documentation and/or other materials provided with the distribution. | |||
| THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER AND CONTRIBUTORS | |||
| ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | |||
| LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | |||
| A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | |||
| HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
| SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
| LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, | |||
| DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | |||
| THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | |||
| (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | |||
| OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |||
| @@ -0,0 +1,25 @@ | |||
| ## Process this file with automake to produce Makefile.in | |||
| if TRE_AGREP | |||
| agrep_dirs = src doc | |||
| else | |||
| agrep_dirs = | |||
| endif | |||
| SUBDIRS = lib $(agrep_dirs) tests utils po m4 | |||
| EXTRA_DIST = \ | |||
| LICENSE \ | |||
| win32/tre-config.h win32/config.h \ | |||
| win32/tre.dsw \ | |||
| win32/tre.dsp win32/tre.def \ | |||
| win32/retest.dsp \ | |||
| python/tre-python.c \ | |||
| python/setup.py \ | |||
| python/example.py | |||
| ACLOCAL_AMFLAGS = -I m4 | |||
| AC_CONFIG_AUX_DIR = utils | |||
| pkgconfigdir = $(libdir)/pkgconfig | |||
| pkgconfig_DATA = tre.pc | |||
| @@ -0,0 +1,713 @@ | |||
| # Makefile.in generated by automake 1.10.1 from Makefile.am. | |||
| # @configure_input@ | |||
| # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, | |||
| # 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. | |||
| # This Makefile.in is free software; the Free Software Foundation | |||
| # gives unlimited permission to copy and/or distribute it, | |||
| # with or without modifications, as long as this notice is preserved. | |||
| # This program is distributed in the hope that it will be useful, | |||
| # but WITHOUT ANY WARRANTY, to the extent permitted by law; without | |||
| # even the implied warranty of MERCHANTABILITY or FITNESS FOR A | |||
| # PARTICULAR PURPOSE. | |||
| @SET_MAKE@ | |||
| VPATH = @srcdir@ | |||
| pkgdatadir = $(datadir)/@PACKAGE@ | |||
| pkglibdir = $(libdir)/@PACKAGE@ | |||
| pkgincludedir = $(includedir)/@PACKAGE@ | |||
| am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd | |||
| install_sh_DATA = $(install_sh) -c -m 644 | |||
| install_sh_PROGRAM = $(install_sh) -c | |||
| install_sh_SCRIPT = $(install_sh) -c | |||
| INSTALL_HEADER = $(INSTALL_DATA) | |||
| transform = $(program_transform_name) | |||
| NORMAL_INSTALL = : | |||
| PRE_INSTALL = : | |||
| POST_INSTALL = : | |||
| NORMAL_UNINSTALL = : | |||
| PRE_UNINSTALL = : | |||
| POST_UNINSTALL = : | |||
| build_triplet = @build@ | |||
| host_triplet = @host@ | |||
| target_triplet = @target@ | |||
| subdir = . | |||
| DIST_COMMON = README $(am__configure_deps) $(srcdir)/Makefile.am \ | |||
| $(srcdir)/Makefile.in $(srcdir)/config.h.in \ | |||
| $(srcdir)/tre.pc.in $(srcdir)/tre.spec.in \ | |||
| $(top_srcdir)/configure ABOUT-NLS AUTHORS ChangeLog INSTALL \ | |||
| NEWS THANKS TODO | |||
| ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 | |||
| am__aclocal_m4_deps = $(top_srcdir)/m4/ac_libtool_tags.m4 \ | |||
| $(top_srcdir)/m4/ax_check_funcs_comp.m4 \ | |||
| $(top_srcdir)/m4/ax_check_sign.m4 \ | |||
| $(top_srcdir)/m4/ax_decl_wchar_max.m4 \ | |||
| $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ | |||
| $(top_srcdir)/m4/intlmacosx.m4 $(top_srcdir)/m4/lib-ld.m4 \ | |||
| $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ | |||
| $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ | |||
| $(top_srcdir)/m4/progtest.m4 \ | |||
| $(top_srcdir)/m4/vl_prog_cc_warnings.m4 \ | |||
| $(top_srcdir)/configure.ac | |||
| am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ | |||
| $(ACLOCAL_M4) | |||
| am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \ | |||
| configure.lineno config.status.lineno | |||
| mkinstalldirs = $(SHELL) $(top_srcdir)/utils/mkinstalldirs | |||
| CONFIG_HEADER = config.h $(top_builddir)/lib/tre-config.h | |||
| CONFIG_CLEAN_FILES = tre.pc tre.spec | |||
| SOURCES = | |||
| DIST_SOURCES = | |||
| RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ | |||
| html-recursive info-recursive install-data-recursive \ | |||
| install-dvi-recursive install-exec-recursive \ | |||
| install-html-recursive install-info-recursive \ | |||
| install-pdf-recursive install-ps-recursive install-recursive \ | |||
| installcheck-recursive installdirs-recursive pdf-recursive \ | |||
| ps-recursive uninstall-recursive | |||
| am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; | |||
| am__vpath_adj = case $$p in \ | |||
| $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ | |||
| *) f=$$p;; \ | |||
| esac; | |||
| am__strip_dir = `echo $$p | sed -e 's|^.*/||'`; | |||
| am__installdirs = "$(DESTDIR)$(pkgconfigdir)" | |||
| pkgconfigDATA_INSTALL = $(INSTALL_DATA) | |||
| DATA = $(pkgconfig_DATA) | |||
| RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ | |||
| distclean-recursive maintainer-clean-recursive | |||
| ETAGS = etags | |||
| CTAGS = ctags | |||
| DIST_SUBDIRS = lib src doc tests utils po m4 | |||
| DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) | |||
| distdir = $(PACKAGE)-$(VERSION) | |||
| top_distdir = $(distdir) | |||
| am__remove_distdir = \ | |||
| { test ! -d $(distdir) \ | |||
| || { find $(distdir) -type d ! -perm -200 -exec chmod u+w {} ';' \ | |||
| && rm -fr $(distdir); }; } | |||
| DIST_ARCHIVES = $(distdir).tar.gz | |||
| GZIP_ENV = --best | |||
| distuninstallcheck_listfiles = find . -type f -print | |||
| distcleancheck_listfiles = find . -type f -print | |||
| ACLOCAL = @ACLOCAL@ | |||
| ALLOCA = @ALLOCA@ | |||
| AMTAR = @AMTAR@ | |||
| AR = @AR@ | |||
| AS = @AS@ | |||
| AUTOCONF = @AUTOCONF@ | |||
| AUTOHEADER = @AUTOHEADER@ | |||
| AUTOMAKE = @AUTOMAKE@ | |||
| AWK = @AWK@ | |||
| CC = @CC@ | |||
| CCDEPMODE = @CCDEPMODE@ | |||
| CFLAGS = @CFLAGS@ | |||
| CPP = @CPP@ | |||
| CPPFLAGS = @CPPFLAGS@ | |||
| CYGPATH_W = @CYGPATH_W@ | |||
| DEFS = @DEFS@ | |||
| DEPDIR = @DEPDIR@ | |||
| DLLTOOL = @DLLTOOL@ | |||
| DSYMUTIL = @DSYMUTIL@ | |||
| ECHO = @ECHO@ | |||
| ECHO_C = @ECHO_C@ | |||
| ECHO_N = @ECHO_N@ | |||
| ECHO_T = @ECHO_T@ | |||
| EGREP = @EGREP@ | |||
| EXEEXT = @EXEEXT@ | |||
| GETTEXT_MACRO_VERSION = @GETTEXT_MACRO_VERSION@ | |||
| GMSGFMT = @GMSGFMT@ | |||
| GMSGFMT_015 = @GMSGFMT_015@ | |||
| GREP = @GREP@ | |||
| INSTALL = @INSTALL@ | |||
| INSTALL_DATA = @INSTALL_DATA@ | |||
| INSTALL_PROGRAM = @INSTALL_PROGRAM@ | |||
| INSTALL_SCRIPT = @INSTALL_SCRIPT@ | |||
| INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ | |||
| INTLLIBS = @INTLLIBS@ | |||
| INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ | |||
| LDFLAGS = @LDFLAGS@ | |||
| LIBICONV = @LIBICONV@ | |||
| LIBINTL = @LIBINTL@ | |||
| LIBOBJS = @LIBOBJS@ | |||
| LIBS = @LIBS@ | |||
| LIBTOOL = @LIBTOOL@ | |||
| LN_S = @LN_S@ | |||
| LTLIBICONV = @LTLIBICONV@ | |||
| LTLIBINTL = @LTLIBINTL@ | |||
| LTLIBOBJS = @LTLIBOBJS@ | |||
| MAKEINFO = @MAKEINFO@ | |||
| MKDIR_P = @MKDIR_P@ | |||
| MSGFMT = @MSGFMT@ | |||
| MSGFMT_015 = @MSGFMT_015@ | |||
| MSGMERGE = @MSGMERGE@ | |||
| NMEDIT = @NMEDIT@ | |||
| OBJDUMP = @OBJDUMP@ | |||
| OBJEXT = @OBJEXT@ | |||
| PACKAGE = @PACKAGE@ | |||
| PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ | |||
| PACKAGE_NAME = @PACKAGE_NAME@ | |||
| PACKAGE_STRING = @PACKAGE_STRING@ | |||
| PACKAGE_TARNAME = @PACKAGE_TARNAME@ | |||
| PACKAGE_VERSION = @PACKAGE_VERSION@ | |||
| PATH_SEPARATOR = @PATH_SEPARATOR@ | |||
| POSUB = @POSUB@ | |||
| RANLIB = @RANLIB@ | |||
| SED = @SED@ | |||
| SET_MAKE = @SET_MAKE@ | |||
| SHELL = @SHELL@ | |||
| STRIP = @STRIP@ | |||
| TRE_VERSION = @TRE_VERSION@ | |||
| USE_NLS = @USE_NLS@ | |||
| VERSION = @VERSION@ | |||
| XGETTEXT = @XGETTEXT@ | |||
| XGETTEXT_015 = @XGETTEXT_015@ | |||
| XGETTEXT_EXTRA_OPTIONS = @XGETTEXT_EXTRA_OPTIONS@ | |||
| abs_builddir = @abs_builddir@ | |||
| abs_srcdir = @abs_srcdir@ | |||
| abs_top_builddir = @abs_top_builddir@ | |||
| abs_top_srcdir = @abs_top_srcdir@ | |||
| ac_ct_CC = @ac_ct_CC@ | |||
| am__include = @am__include@ | |||
| am__leading_dot = @am__leading_dot@ | |||
| am__quote = @am__quote@ | |||
| am__tar = @am__tar@ | |||
| am__untar = @am__untar@ | |||
| bindir = @bindir@ | |||
| build = @build@ | |||
| build_alias = @build_alias@ | |||
| build_cpu = @build_cpu@ | |||
| build_os = @build_os@ | |||
| build_vendor = @build_vendor@ | |||
| builddir = @builddir@ | |||
| datadir = @datadir@ | |||
| datarootdir = @datarootdir@ | |||
| docdir = @docdir@ | |||
| dvidir = @dvidir@ | |||
| exec_prefix = @exec_prefix@ | |||
| host = @host@ | |||
| host_alias = @host_alias@ | |||
| host_cpu = @host_cpu@ | |||
| host_os = @host_os@ | |||
| host_vendor = @host_vendor@ | |||
| htmldir = @htmldir@ | |||
| includedir = @includedir@ | |||
| infodir = @infodir@ | |||
| install_sh = @install_sh@ | |||
| libdir = @libdir@ | |||
| libexecdir = @libexecdir@ | |||
| localedir = @localedir@ | |||
| localstatedir = @localstatedir@ | |||
| mandir = @mandir@ | |||
| mkdir_p = @mkdir_p@ | |||
| oldincludedir = @oldincludedir@ | |||
| pdfdir = @pdfdir@ | |||
| prefix = @prefix@ | |||
| program_transform_name = @program_transform_name@ | |||
| psdir = @psdir@ | |||
| sbindir = @sbindir@ | |||
| sharedstatedir = @sharedstatedir@ | |||
| srcdir = @srcdir@ | |||
| sysconfdir = @sysconfdir@ | |||
| target = @target@ | |||
| target_alias = @target_alias@ | |||
| target_cpu = @target_cpu@ | |||
| target_os = @target_os@ | |||
| target_vendor = @target_vendor@ | |||
| top_builddir = @top_builddir@ | |||
| top_srcdir = @top_srcdir@ | |||
| @TRE_AGREP_FALSE@agrep_dirs = | |||
| @TRE_AGREP_TRUE@agrep_dirs = src doc | |||
| SUBDIRS = lib $(agrep_dirs) tests utils po m4 | |||
| EXTRA_DIST = \ | |||
| LICENSE \ | |||
| win32/tre-config.h win32/config.h \ | |||
| win32/tre.dsw \ | |||
| win32/tre.dsp win32/tre.def \ | |||
| win32/retest.dsp \ | |||
| python/tre-python.c \ | |||
| python/setup.py \ | |||
| python/example.py | |||
| ACLOCAL_AMFLAGS = -I m4 | |||
| AC_CONFIG_AUX_DIR = utils | |||
| pkgconfigdir = $(libdir)/pkgconfig | |||
| pkgconfig_DATA = tre.pc | |||
| all: config.h | |||
| $(MAKE) $(AM_MAKEFLAGS) all-recursive | |||
| .SUFFIXES: | |||
| am--refresh: | |||
| @: | |||
| $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) | |||
| @for dep in $?; do \ | |||
| case '$(am__configure_deps)' in \ | |||
| *$$dep*) \ | |||
| echo ' cd $(srcdir) && $(AUTOMAKE) --foreign '; \ | |||
| cd $(srcdir) && $(AUTOMAKE) --foreign \ | |||
| && exit 0; \ | |||
| exit 1;; \ | |||
| esac; \ | |||
| done; \ | |||
| echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign Makefile'; \ | |||
| cd $(top_srcdir) && \ | |||
| $(AUTOMAKE) --foreign Makefile | |||
| .PRECIOUS: Makefile | |||
| Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status | |||
| @case '$?' in \ | |||
| *config.status*) \ | |||
| echo ' $(SHELL) ./config.status'; \ | |||
| $(SHELL) ./config.status;; \ | |||
| *) \ | |||
| echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe)'; \ | |||
| cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe);; \ | |||
| esac; | |||
| $(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) | |||
| $(SHELL) ./config.status --recheck | |||
| $(top_srcdir)/configure: $(am__configure_deps) | |||
| cd $(srcdir) && $(AUTOCONF) | |||
| $(ACLOCAL_M4): $(am__aclocal_m4_deps) | |||
| cd $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS) | |||
| config.h: stamp-h1 | |||
| @if test ! -f $@; then \ | |||
| rm -f stamp-h1; \ | |||
| $(MAKE) $(AM_MAKEFLAGS) stamp-h1; \ | |||
| else :; fi | |||
| stamp-h1: $(srcdir)/config.h.in $(top_builddir)/config.status | |||
| @rm -f stamp-h1 | |||
| cd $(top_builddir) && $(SHELL) ./config.status config.h | |||
| $(srcdir)/config.h.in: $(am__configure_deps) | |||
| cd $(top_srcdir) && $(AUTOHEADER) | |||
| rm -f stamp-h1 | |||
| touch $@ | |||
| distclean-hdr: | |||
| -rm -f config.h stamp-h1 | |||
| tre.pc: $(top_builddir)/config.status $(srcdir)/tre.pc.in | |||
| cd $(top_builddir) && $(SHELL) ./config.status $@ | |||
| tre.spec: $(top_builddir)/config.status $(srcdir)/tre.spec.in | |||
| cd $(top_builddir) && $(SHELL) ./config.status $@ | |||
| mostlyclean-libtool: | |||
| -rm -f *.lo | |||
| clean-libtool: | |||
| -rm -rf .libs _libs | |||
| distclean-libtool: | |||
| -rm -f libtool | |||
| install-pkgconfigDATA: $(pkgconfig_DATA) | |||
| @$(NORMAL_INSTALL) | |||
| test -z "$(pkgconfigdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgconfigdir)" | |||
| @list='$(pkgconfig_DATA)'; for p in $$list; do \ | |||
| if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ | |||
| f=$(am__strip_dir) \ | |||
| echo " $(pkgconfigDATA_INSTALL) '$$d$$p' '$(DESTDIR)$(pkgconfigdir)/$$f'"; \ | |||
| $(pkgconfigDATA_INSTALL) "$$d$$p" "$(DESTDIR)$(pkgconfigdir)/$$f"; \ | |||
| done | |||
| uninstall-pkgconfigDATA: | |||
| @$(NORMAL_UNINSTALL) | |||
| @list='$(pkgconfig_DATA)'; for p in $$list; do \ | |||
| f=$(am__strip_dir) \ | |||
| echo " rm -f '$(DESTDIR)$(pkgconfigdir)/$$f'"; \ | |||
| rm -f "$(DESTDIR)$(pkgconfigdir)/$$f"; \ | |||
| done | |||
| # This directory's subdirectories are mostly independent; you can cd | |||
| # into them and run `make' without going through this Makefile. | |||
| # To change the values of `make' variables: instead of editing Makefiles, | |||
| # (1) if the variable is set in `config.status', edit `config.status' | |||
| # (which will cause the Makefiles to be regenerated when you run `make'); | |||
| # (2) otherwise, pass the desired values on the `make' command line. | |||
| $(RECURSIVE_TARGETS): | |||
| @failcom='exit 1'; \ | |||
| for f in x $$MAKEFLAGS; do \ | |||
| case $$f in \ | |||
| *=* | --[!k]*);; \ | |||
| *k*) failcom='fail=yes';; \ | |||
| esac; \ | |||
| done; \ | |||
| dot_seen=no; \ | |||
| target=`echo $@ | sed s/-recursive//`; \ | |||
| list='$(SUBDIRS)'; for subdir in $$list; do \ | |||
| echo "Making $$target in $$subdir"; \ | |||
| if test "$$subdir" = "."; then \ | |||
| dot_seen=yes; \ | |||
| local_target="$$target-am"; \ | |||
| else \ | |||
| local_target="$$target"; \ | |||
| fi; \ | |||
| (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ | |||
| || eval $$failcom; \ | |||
| done; \ | |||
| if test "$$dot_seen" = "no"; then \ | |||
| $(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \ | |||
| fi; test -z "$$fail" | |||
| $(RECURSIVE_CLEAN_TARGETS): | |||
| @failcom='exit 1'; \ | |||
| for f in x $$MAKEFLAGS; do \ | |||
| case $$f in \ | |||
| *=* | --[!k]*);; \ | |||
| *k*) failcom='fail=yes';; \ | |||
| esac; \ | |||
| done; \ | |||
| dot_seen=no; \ | |||
| case "$@" in \ | |||
| distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \ | |||
| *) list='$(SUBDIRS)' ;; \ | |||
| esac; \ | |||
| rev=''; for subdir in $$list; do \ | |||
| if test "$$subdir" = "."; then :; else \ | |||
| rev="$$subdir $$rev"; \ | |||
| fi; \ | |||
| done; \ | |||
| rev="$$rev ."; \ | |||
| target=`echo $@ | sed s/-recursive//`; \ | |||
| for subdir in $$rev; do \ | |||
| echo "Making $$target in $$subdir"; \ | |||
| if test "$$subdir" = "."; then \ | |||
| local_target="$$target-am"; \ | |||
| else \ | |||
| local_target="$$target"; \ | |||
| fi; \ | |||
| (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ | |||
| || eval $$failcom; \ | |||
| done && test -z "$$fail" | |||
| tags-recursive: | |||
| list='$(SUBDIRS)'; for subdir in $$list; do \ | |||
| test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) tags); \ | |||
| done | |||
| ctags-recursive: | |||
| list='$(SUBDIRS)'; for subdir in $$list; do \ | |||
| test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) ctags); \ | |||
| done | |||
| ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) | |||
| list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| mkid -fID $$unique | |||
| tags: TAGS | |||
| TAGS: tags-recursive $(HEADERS) $(SOURCES) config.h.in $(TAGS_DEPENDENCIES) \ | |||
| $(TAGS_FILES) $(LISP) | |||
| tags=; \ | |||
| here=`pwd`; \ | |||
| if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \ | |||
| include_option=--etags-include; \ | |||
| empty_fix=.; \ | |||
| else \ | |||
| include_option=--include; \ | |||
| empty_fix=; \ | |||
| fi; \ | |||
| list='$(SUBDIRS)'; for subdir in $$list; do \ | |||
| if test "$$subdir" = .; then :; else \ | |||
| test ! -f $$subdir/TAGS || \ | |||
| tags="$$tags $$include_option=$$here/$$subdir/TAGS"; \ | |||
| fi; \ | |||
| done; \ | |||
| list='$(SOURCES) $(HEADERS) config.h.in $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ | |||
| test -n "$$unique" || unique=$$empty_fix; \ | |||
| $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ | |||
| $$tags $$unique; \ | |||
| fi | |||
| ctags: CTAGS | |||
| CTAGS: ctags-recursive $(HEADERS) $(SOURCES) config.h.in $(TAGS_DEPENDENCIES) \ | |||
| $(TAGS_FILES) $(LISP) | |||
| tags=; \ | |||
| list='$(SOURCES) $(HEADERS) config.h.in $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| test -z "$(CTAGS_ARGS)$$tags$$unique" \ | |||
| || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ | |||
| $$tags $$unique | |||
| GTAGS: | |||
| here=`$(am__cd) $(top_builddir) && pwd` \ | |||
| && cd $(top_srcdir) \ | |||
| && gtags -i $(GTAGS_ARGS) $$here | |||
| distclean-tags: | |||
| -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags | |||
| distdir: $(DISTFILES) | |||
| $(am__remove_distdir) | |||
| test -d $(distdir) || mkdir $(distdir) | |||
| @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| list='$(DISTFILES)'; \ | |||
| dist_files=`for file in $$list; do echo $$file; done | \ | |||
| sed -e "s|^$$srcdirstrip/||;t" \ | |||
| -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ | |||
| case $$dist_files in \ | |||
| */*) $(MKDIR_P) `echo "$$dist_files" | \ | |||
| sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ | |||
| sort -u` ;; \ | |||
| esac; \ | |||
| for file in $$dist_files; do \ | |||
| if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ | |||
| if test -d $$d/$$file; then \ | |||
| dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ | |||
| if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ | |||
| cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ | |||
| fi; \ | |||
| cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ | |||
| else \ | |||
| test -f $(distdir)/$$file \ | |||
| || cp -p $$d/$$file $(distdir)/$$file \ | |||
| || exit 1; \ | |||
| fi; \ | |||
| done | |||
| list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ | |||
| if test "$$subdir" = .; then :; else \ | |||
| test -d "$(distdir)/$$subdir" \ | |||
| || $(MKDIR_P) "$(distdir)/$$subdir" \ | |||
| || exit 1; \ | |||
| distdir=`$(am__cd) $(distdir) && pwd`; \ | |||
| top_distdir=`$(am__cd) $(top_distdir) && pwd`; \ | |||
| (cd $$subdir && \ | |||
| $(MAKE) $(AM_MAKEFLAGS) \ | |||
| top_distdir="$$top_distdir" \ | |||
| distdir="$$distdir/$$subdir" \ | |||
| am__remove_distdir=: \ | |||
| am__skip_length_check=: \ | |||
| distdir) \ | |||
| || exit 1; \ | |||
| fi; \ | |||
| done | |||
| -find $(distdir) -type d ! -perm -777 -exec chmod a+rwx {} \; -o \ | |||
| ! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \ | |||
| ! -type d ! -perm -400 -exec chmod a+r {} \; -o \ | |||
| ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \ | |||
| || chmod -R a+r $(distdir) | |||
| dist-gzip: distdir | |||
| tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz | |||
| $(am__remove_distdir) | |||
| dist-bzip2: distdir | |||
| tardir=$(distdir) && $(am__tar) | bzip2 -9 -c >$(distdir).tar.bz2 | |||
| $(am__remove_distdir) | |||
| dist-lzma: distdir | |||
| tardir=$(distdir) && $(am__tar) | lzma -9 -c >$(distdir).tar.lzma | |||
| $(am__remove_distdir) | |||
| dist-tarZ: distdir | |||
| tardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z | |||
| $(am__remove_distdir) | |||
| dist-shar: distdir | |||
| shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz | |||
| $(am__remove_distdir) | |||
| dist-zip: distdir | |||
| -rm -f $(distdir).zip | |||
| zip -rq $(distdir).zip $(distdir) | |||
| $(am__remove_distdir) | |||
| dist dist-all: distdir | |||
| tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz | |||
| $(am__remove_distdir) | |||
| # This target untars the dist file and tries a VPATH configuration. Then | |||
| # it guarantees that the distribution is self-contained by making another | |||
| # tarfile. | |||
| distcheck: dist | |||
| case '$(DIST_ARCHIVES)' in \ | |||
| *.tar.gz*) \ | |||
| GZIP=$(GZIP_ENV) gunzip -c $(distdir).tar.gz | $(am__untar) ;;\ | |||
| *.tar.bz2*) \ | |||
| bunzip2 -c $(distdir).tar.bz2 | $(am__untar) ;;\ | |||
| *.tar.lzma*) \ | |||
| unlzma -c $(distdir).tar.lzma | $(am__untar) ;;\ | |||
| *.tar.Z*) \ | |||
| uncompress -c $(distdir).tar.Z | $(am__untar) ;;\ | |||
| *.shar.gz*) \ | |||
| GZIP=$(GZIP_ENV) gunzip -c $(distdir).shar.gz | unshar ;;\ | |||
| *.zip*) \ | |||
| unzip $(distdir).zip ;;\ | |||
| esac | |||
| chmod -R a-w $(distdir); chmod a+w $(distdir) | |||
| mkdir $(distdir)/_build | |||
| mkdir $(distdir)/_inst | |||
| chmod a-w $(distdir) | |||
| dc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\/]:[\\/],/,'` \ | |||
| && dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \ | |||
| && cd $(distdir)/_build \ | |||
| && ../configure --srcdir=.. --prefix="$$dc_install_base" \ | |||
| $(DISTCHECK_CONFIGURE_FLAGS) \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) dvi \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) check \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) install \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) installcheck \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) uninstall \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir="$$dc_install_base" \ | |||
| distuninstallcheck \ | |||
| && chmod -R a-w "$$dc_install_base" \ | |||
| && ({ \ | |||
| (cd ../.. && umask 077 && mkdir "$$dc_destdir") \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" install \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" uninstall \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" \ | |||
| distuninstallcheck_dir="$$dc_destdir" distuninstallcheck; \ | |||
| } || { rm -rf "$$dc_destdir"; exit 1; }) \ | |||
| && rm -rf "$$dc_destdir" \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) dist \ | |||
| && rm -rf $(DIST_ARCHIVES) \ | |||
| && $(MAKE) $(AM_MAKEFLAGS) distcleancheck | |||
| $(am__remove_distdir) | |||
| @(echo "$(distdir) archives ready for distribution: "; \ | |||
| list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \ | |||
| sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x' | |||
| distuninstallcheck: | |||
| @cd $(distuninstallcheck_dir) \ | |||
| && test `$(distuninstallcheck_listfiles) | wc -l` -le 1 \ | |||
| || { echo "ERROR: files left after uninstall:" ; \ | |||
| if test -n "$(DESTDIR)"; then \ | |||
| echo " (check DESTDIR support)"; \ | |||
| fi ; \ | |||
| $(distuninstallcheck_listfiles) ; \ | |||
| exit 1; } >&2 | |||
| distcleancheck: distclean | |||
| @if test '$(srcdir)' = . ; then \ | |||
| echo "ERROR: distcleancheck can only run from a VPATH build" ; \ | |||
| exit 1 ; \ | |||
| fi | |||
| @test `$(distcleancheck_listfiles) | wc -l` -eq 0 \ | |||
| || { echo "ERROR: files left in build directory after distclean:" ; \ | |||
| $(distcleancheck_listfiles) ; \ | |||
| exit 1; } >&2 | |||
| check-am: all-am | |||
| check: check-recursive | |||
| all-am: Makefile $(DATA) config.h | |||
| installdirs: installdirs-recursive | |||
| installdirs-am: | |||
| for dir in "$(DESTDIR)$(pkgconfigdir)"; do \ | |||
| test -z "$$dir" || $(MKDIR_P) "$$dir"; \ | |||
| done | |||
| install: install-recursive | |||
| install-exec: install-exec-recursive | |||
| install-data: install-data-recursive | |||
| uninstall: uninstall-recursive | |||
| install-am: all-am | |||
| @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am | |||
| installcheck: installcheck-recursive | |||
| install-strip: | |||
| $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ | |||
| install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ | |||
| `test -z '$(STRIP)' || \ | |||
| echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install | |||
| mostlyclean-generic: | |||
| clean-generic: | |||
| distclean-generic: | |||
| -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) | |||
| maintainer-clean-generic: | |||
| @echo "This command is intended for maintainers to use" | |||
| @echo "it deletes files that may require special tools to rebuild." | |||
| clean: clean-recursive | |||
| clean-am: clean-generic clean-libtool mostlyclean-am | |||
| distclean: distclean-recursive | |||
| -rm -f $(am__CONFIG_DISTCLEAN_FILES) | |||
| -rm -f Makefile | |||
| distclean-am: clean-am distclean-generic distclean-hdr \ | |||
| distclean-libtool distclean-tags | |||
| dvi: dvi-recursive | |||
| dvi-am: | |||
| html: html-recursive | |||
| info: info-recursive | |||
| info-am: | |||
| install-data-am: install-pkgconfigDATA | |||
| install-dvi: install-dvi-recursive | |||
| install-exec-am: | |||
| install-html: install-html-recursive | |||
| install-info: install-info-recursive | |||
| install-man: | |||
| install-pdf: install-pdf-recursive | |||
| install-ps: install-ps-recursive | |||
| installcheck-am: | |||
| maintainer-clean: maintainer-clean-recursive | |||
| -rm -f $(am__CONFIG_DISTCLEAN_FILES) | |||
| -rm -rf $(top_srcdir)/autom4te.cache | |||
| -rm -f Makefile | |||
| maintainer-clean-am: distclean-am maintainer-clean-generic | |||
| mostlyclean: mostlyclean-recursive | |||
| mostlyclean-am: mostlyclean-generic mostlyclean-libtool | |||
| pdf: pdf-recursive | |||
| pdf-am: | |||
| ps: ps-recursive | |||
| ps-am: | |||
| uninstall-am: uninstall-pkgconfigDATA | |||
| .MAKE: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) install-am \ | |||
| install-strip | |||
| .PHONY: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) CTAGS GTAGS \ | |||
| all all-am am--refresh check check-am clean clean-generic \ | |||
| clean-libtool ctags ctags-recursive dist dist-all dist-bzip2 \ | |||
| dist-gzip dist-lzma dist-shar dist-tarZ dist-zip distcheck \ | |||
| distclean distclean-generic distclean-hdr distclean-libtool \ | |||
| distclean-tags distcleancheck distdir distuninstallcheck dvi \ | |||
| dvi-am html html-am info info-am install install-am \ | |||
| install-data install-data-am install-dvi install-dvi-am \ | |||
| install-exec install-exec-am install-html install-html-am \ | |||
| install-info install-info-am install-man install-pdf \ | |||
| install-pdf-am install-pkgconfigDATA install-ps install-ps-am \ | |||
| install-strip installcheck installcheck-am installdirs \ | |||
| installdirs-am maintainer-clean maintainer-clean-generic \ | |||
| mostlyclean mostlyclean-generic mostlyclean-libtool pdf pdf-am \ | |||
| ps ps-am tags tags-recursive uninstall uninstall-am \ | |||
| uninstall-pkgconfigDATA | |||
| # Tell versions [3.59,3.63) of GNU make to not export all variables. | |||
| # Otherwise a system limit (for SysV at least) may be exceeded. | |||
| .NOEXPORT: | |||
| @@ -0,0 +1,243 @@ | |||
| Version 0.8.0 | |||
| - Added tre_ prefix to all functions exported from libtre. This | |||
| changes the binary interface (ABI). The old source interface | |||
| (API) is still available in <tre/regex.h>. New programs should | |||
| use <tre/tre.h>. | |||
| - Visual C++ 6 project files replaced with Visual Studio 2008 files. | |||
| - Bug fixes. | |||
| Version 0.7.6 | |||
| - The license is changed from LGPL to a BSD-style license. The new | |||
| license is essentially the same as the "2 clause" BSD-style | |||
| license used in NetBSD. See the file LICENSE for details. | |||
| - No longer using gnulib due to potential license conflicts. | |||
| - Bug fixes. | |||
| Version 0.7.5 | |||
| - Swedish translation added. | |||
| - Makefile and source code distribution problems fixed. | |||
| - Documentation updates. | |||
| - Adding a "+" or "*" after another repetition operator is now an | |||
| error instead of an application of that operator and gives the | |||
| REG_BADRPT error. Adding a "?" means matching as few characters | |||
| as possible and is still allowed. | |||
| This change was made to avoid confusion with "possessive" | |||
| (non-backtracking) quantifiers. In Java (and .NET?) adding a "+" | |||
| means that the matcher doesn't backtrack over that point. In | |||
| previous versions of TRE adding a "+" or "*" caused the | |||
| backtracking matcher to backtrack a lot more instead of less. In | |||
| some cases this caused very slow execution. | |||
| - New agrep command line option -q (--quiet, --silent). | |||
| - Bug fixes: | |||
| - agrep now correctly returns exit code 1 when no matches found. | |||
| - Fixed regexp parser bug affecting big-endian 64 bit | |||
| architectures (sparc, ppc). The bug caused all regexps to match | |||
| an empty string and nothing else. | |||
| - Fixed agrep memory usage problems when reading from pipes. | |||
| Version 0.7.4 | |||
| - TRE now builds cleanly on x86_64 and other 64 bit platforms. | |||
| There was a large number of (basically harmless) compiler warnings | |||
| in previous versions. | |||
| - Now builds and works on Cygwin and MinGW. Libtool was updated to | |||
| a version which works on these platforms, and the Makefiles and | |||
| configure scripts were adjusted so that DLLs are now built on | |||
| these platforms. | |||
| - agrep now handles long command line options on all platforms. | |||
| - Bug report email address is now tre-general@lists.laurikari.net. | |||
| - Many bug fixes, including: | |||
| - The RPM spec file now works with recent rpmbuild versions | |||
| - agrep no longer includes record delimiters in records, so for | |||
| example "echo foo | agrep 'foo$'" works as expected. | |||
| - agrep help texts and man page updated. | |||
| Version 0.7.3 | |||
| - The license has been changed from GPL to LGPL. | |||
| - New command line option to agrep: --show-position | |||
| - New REG_UNGREEDY cflags and 'U' pattern modifier. | |||
| - Bug fixes. | |||
| Version 0.7.2 | |||
| - Bug fixes. | |||
| Version 0.7.1 | |||
| - New command line options to agrep: --delimiter-after, --color | |||
| - Man page for agrep added. | |||
| - Some bugs fixed. | |||
| Version 0.7.0 | |||
| - reguexec() added. | |||
| - tre_have_backrefs() and tre_have_approx() added. | |||
| - New syntax: \Q, \E, \x1B, \x{263a}, (?inr-inr), (?inr-inr:regex). | |||
| - New compilation flag REG_RIGHT_ASSOC. | |||
| - New execution flags REG_APPROX_MATCHER and REG_BACKTRACKING_MATCHER. | |||
| - Included Python language bindings contributed by Nikolai SAOUKH. | |||
| - Several bugs and compilation problems fixed. | |||
| Version 0.6.8 | |||
| - Fixed to use iswctype() if found instead of always using | |||
| iswalpha() and friends. Now [[:blank:]] should work again on | |||
| systems where iswctype() is available. | |||
| Version 0.6.7 | |||
| - Fixed the -h (--no-filename) option of agrep to work again. | |||
| - Added the -y option to agrep. It does nothing, and exists only | |||
| for compatibility with the non-free version of agrep. | |||
| - Fixed bugs: handling null bytes in multibyte mode, exponential | |||
| memory usage problem when using lots of macros (e.g. \s or \d) in | |||
| a regexp, and bugs in expanding {m,n} repeats (still!). | |||
| - wctype() and iswctype() are no longer required for wchar support, | |||
| iswalpha() and friends will be used instead if wctype() and | |||
| iswctype() are not found. | |||
| - Added support for compiling against libutf8. | |||
| - Added the tre_config() function to get information about the | |||
| optional features compiled in the TRE library. Also added | |||
| tre_version(). | |||
| - Some documentation updates. | |||
| Version 0.6.6 | |||
| - Fixed bugs which occurred sometimes when "{m,n}" repeats were used | |||
| in conjunction with "*", "+", or "?". | |||
| - Added the -H (--with-filename) option to agrep. | |||
| Version 0.6.5 | |||
| - Fixed bug which occurred whine several "{m,n}" repeats were used | |||
| in one regex. | |||
| - Fixed several bugs related to REG_NOSUB or NULL pmatch[] arrays | |||
| being used for regexec(). | |||
| - C++ or Fortran compilers no longer checked by the configure | |||
| script. | |||
| - Some documentation additions. | |||
| Version 0.6.4 | |||
| - Fixed bug in handling iterations (like "+" and "*") inside "{m,n}" | |||
| repeats. This should get rid of performance problems and | |||
| incorrect results with certain regexps involving "{m,n}" repeats. | |||
| Version 0.6.3 | |||
| - Fixed back references when REG_NOSUB is used. | |||
| - Compilation errors and warnings fixed. Now this should compile on | |||
| systems that don't have wide character support, like OpenBSD, and | |||
| works on 64 bit machines. | |||
| Version 0.6.2 | |||
| - Bug fixes. | |||
| Version 0.6.1 | |||
| - Bug fixes. | |||
| - Some documentation updates. | |||
| Version 0.6.0 | |||
| - The doc/ directory is now actually included in source | |||
| distributions (oops). | |||
| - Bug fixes. | |||
| - alloca() is no longer a requirement. The configure script still | |||
| looks for it, and it is used if found. | |||
| - New approximate matching syntax. The new syntax allows | |||
| approximate matching to be done even using the standard regex API | |||
| (match costs are only available when the regaexec() API is used). | |||
| - REG_LITERAL implemented. | |||
| Version 0.5.3 | |||
| - Bug fixes and compilation fixes. | |||
| - Best match mode (-B) for agrep. | |||
| Version 0.5.2 | |||
| - System ABI support. TRE is now by default configured to be | |||
| compatible with the system regex binary interface (by including | |||
| the system regex.h and using the definitions there instead of | |||
| TRE's own). This can be disabled with --disable-system-abi. | |||
| - Added a pkg-config file `tre.pc'. | |||
| - Added support for minimal (non-greedy) repetition operators | |||
| "*?", "+?", "??", and "{m,n}?". They work similarly to the ones | |||
| in Perl, except the number of characters matched is minimized | |||
| instead of the number of repetitions. | |||
| - Added some documentation in the doc/ subdirectory. | |||
| - Bug fixes. | |||
| Version 0.5.1 | |||
| - Bug fixes. | |||
| Version 0.5.0 | |||
| - Approximate matching functions now fill the pmatch[] array of | |||
| submatches if wanted. | |||
| - Support for back referencing (not for approximate matching). | |||
| - Changed approximate matching API to be more easily extendible in | |||
| the future. The match cost is now returned. | |||
| - Bug fixes. | |||
| - Windows project files (original versions contributed by Aymeric | |||
| Moizard <jack@atosc.org>, thanks!). | |||
| Version 0.4.1 | |||
| - Fixed installed headers. | |||
| - Fixed compilation problems. | |||
| Version 0.4.0 | |||
| - The name of the package changed to TRE. | |||
| - New API for approximate regexp matching. | |||
| - New command line utility `agrep' for approximate regexp matching | |||
| in the style of grep. | |||
| - New translation for Finnish (fi) has been added. | |||
| - Optimizations in regexec. | |||
| - Wide character support and multibyte character set support can be | |||
| turned off with --disable-wchar and --disable-multibyte, | |||
| respectively. | |||
| - Lots of bugfixes. | |||
| @@ -0,0 +1,235 @@ | |||
| Introduction | |||
| TRE is a lightweight, robust, and efficient POSIX compliant regexp | |||
| matching library with some exciting features such as approximate | |||
| (fuzzy) matching. | |||
| The matching algorithm used in TRE uses linear worst-case time in | |||
| the length of the text being searched, and quadratic worst-case | |||
| time in the length of the used regular expression. In other words, | |||
| the time complexity of the algorithm is O(M^2N), where M is the | |||
| length of the regular expression and N is the length of the | |||
| text. The used space is also quadratic on the length of the regex, | |||
| but does not depend on the searched string. This quadratic | |||
| behaviour occurs only on pathological cases which are probably very | |||
| rare in practice. | |||
| Features | |||
| TRE is not just yet another regexp matcher. TRE has some features | |||
| which are not there in most free POSIX compatible | |||
| implementations. Most of these features are not present in non-free | |||
| implementations either, for that matter. | |||
| Approximate matching | |||
| Approximate pattern matching allows matches to be approximate, that | |||
| is, allows the matches to be close to the searched pattern under | |||
| some measure of closeness. TRE uses the edit-distance measure (also | |||
| known as the Levenshtein distance) where characters can be | |||
| inserted, deleted, or substituted in the searched text in order to | |||
| get an exact match. Each insertion, deletion, or substitution adds | |||
| the distance, or cost, of the match. TRE can report the matches | |||
| which have a cost lower than some given threshold value. TRE can | |||
| also be used to search for matches with the lowest cost. | |||
| TRE includes a version of the agrep (approximate grep) command line | |||
| tool for approximate regexp matching in the style of grep. Unlike | |||
| other agrep implementations (like the one by Sun Wu and Udi Manber | |||
| from University of Arizona available here) TRE agrep allows full | |||
| regexps of any length, any number of errors, and non-uniform costs | |||
| for insertion, deletion and substitution. | |||
| Strict standard conformance | |||
| POSIX defines the behaviour of regexp functions precisely. TRE | |||
| attempts to conform to these specifications as strictly as | |||
| possible. TRE always returns the correct matches for subpatterns, | |||
| for example. Very few other implementations do this correctly. In | |||
| fact, the only other implementations besides TRE that I am aware of | |||
| (free or not) that get it right are Rx by Tom Lord, Regex++ by John | |||
| Maddock, and the AT&T ast regex by Glenn Fowler and Doug McIlroy. | |||
| The standard TRE tries to conform to is the IEEE Std 1003.1-2001, | |||
| or Open Group Base Specifications Issue 6, commonly referred to as | |||
| "POSIX". It can be found online here. The relevant parts are the | |||
| base specifications on regular expressions (and the rationale) and | |||
| the description of the regcomp() API. | |||
| For an excellent survey on POSIX regexp matchers, see the testregex | |||
| pages by Glenn Fowler of AT&T Labs Research. | |||
| Predictable matching speed | |||
| Because of the matching algorithm used in TRE, the maximum time | |||
| consumed by any regexec() call is always directly proportional to | |||
| the length of the searched string. There is one exception: if back | |||
| references are used, the matching may take time that grows | |||
| exponentially with the length of the string. This is because | |||
| matching back references is an NP complete problem, and almost | |||
| certainly requires exponential time to match in the worst case. | |||
| Predictable and modest memory consumption | |||
| A regexec() call never allocates memory from the heap. TRE | |||
| allocates all the memory it needs during a regcomp() call, and some | |||
| temporary working space from the stack frame for the duration of | |||
| the regexec() call. The amount of temporary space needed is | |||
| constant during matching and does not depend on the searched | |||
| string. For regexps of reasonable size TRE needs less than 50K of | |||
| dynamically allocated memory during the regcomp() call, less than | |||
| 20K for the compiled pattern buffer, and less than two kilobytes of | |||
| temporary working space from the stack frame during a regexec() | |||
| call. There is no time/memory tradeoff. TRE is also small in code | |||
| size; statically linking with TRE increases the executable size | |||
| less than 30K (gcc-3.2, x86, GNU/Linux). | |||
| Wide character and multibyte character set support | |||
| TRE supports multibyte character sets. This makes it possible to | |||
| use regexps seamlessly with, for example, Japanese locales. TRE | |||
| also provides a wide character API. | |||
| Binary pattern and data support | |||
| TRE provides APIs which allow binary zero characters both in | |||
| regexps and searched strings. The standard API cannot be easily | |||
| used to, for example, search for printable words from binary data | |||
| (although it is possible with some hacking). Searching for patterns | |||
| which contain binary zeroes embedded is not possible at all with | |||
| the standard API. | |||
| Completely thread safe | |||
| TRE is completely thread safe. All the exported functions are | |||
| re-entrant, and a single compiled regexp object can be used | |||
| simultaneously in multiple contexts; e.g. in main() and a signal | |||
| handler, or in many threads of a multithreaded application. | |||
| Portable | |||
| TRE is portable across multiple platforms. Here's a table of | |||
| platforms and compilers that have been successfully used to compile | |||
| and run TRE: | |||
| Platform(s) | Compiler(s) | |||
| ----------------------------------+------------ | |||
| AIX 4.3.2 - 5.3.0 | GCC, C for AIX compiler version 5 | |||
| Compaq Tru64 UNIX V5.1A/B | Compaq C V6.4-014 - V6.5-011 | |||
| Cygwin 1.3 - 1.5 | GCC | |||
| Digital UNIX V4.0 | DEC C V5.9-005 | |||
| FreeBSD 4 and above | GCC | |||
| GNU/Linux systems on x86, x86_64, | GCC | |||
| ppc64, s390 | | |||
| HP-UX 10.20- 11.00 | GCC, HP C Compiler | |||
| IRIX 6.5 | GCC, MIPSpro Compilers 7.3.1.3m | |||
| Max OS X | | |||
| NetBSD 1.5 and above | GCC, egcs | |||
| OpenBSD 3.3 and above | GCC | |||
| Solaris 2.7-10 sparc/x86 | GCC, Sun Workshop 6 compilers | |||
| Windows 98 - XP | Microsoft Visual C++ 6.0 | |||
| TRE 0.7.5 should compile without changes on all of the above | |||
| platforms. Tell me if you are using TRE on a platform that is not | |||
| listed above, and I'll add it to the list. Also let me know if TRE | |||
| does not work on a listed platform. | |||
| Depending on the platform, you may need to install libutf8 to get | |||
| wide character and multibyte character set support. | |||
| Free | |||
| TRE is released under a license which is essentially the same as | |||
| the "2 clause" BSD-style license used in NetBSD. See the file | |||
| LICENSE for details. | |||
| Roadmap | |||
| There are currently two features, both related to collating | |||
| elements, missing from 100% POSIX compliance. These are: | |||
| * Support for collating elements (e.g. [[.<X>.]], where <X> is a | |||
| collating element). It is not possible to support | |||
| multi-character collating elements portably, since POSIX does | |||
| not define a way to determine whether a character sequence is a | |||
| multi-character collating element or not. | |||
| * Support for equivalence classes, for example [[=<X>=]], where | |||
| <X> is a collating element. An equivalence class matches any | |||
| character which has the same primary collation weight as | |||
| <X>. Again, POSIX provides no portable mechanism for | |||
| determining the primary collation weight of a collating | |||
| element. | |||
| Note that other portable regexp implementations don't support | |||
| collating elements either. The single exception is Regex++, which | |||
| comes with its own database for collating elements for different | |||
| locales. Support for collating elements and equivalence classes has | |||
| not been widely requested and is not very high on the TODO list at | |||
| the moment. | |||
| These are other features I'm planning to implement real soon now: | |||
| * All the missing GNU extensions enabled in GNU regex, such as | |||
| [[:<:]] and [[:>:]] | |||
| * A REG_SHORTEST regexec() flag for returning the shortest match | |||
| instead of the longest match. | |||
| * Perl-compatible syntax | |||
| [:^class:] | |||
| Matches anything but the characters in class. Note that | |||
| [^[:class:]] works already, this would be just a | |||
| convenience shorthand. | |||
| \A | |||
| Match only at beginning of string | |||
| \Z | |||
| Match only at end of string, or before newline at the end | |||
| \z | |||
| Match only at end of string | |||
| \l | |||
| Lowercase next char (think vi) | |||
| \u | |||
| Uppercase next char (think vi) | |||
| \L | |||
| Lowercase till \E (think vi) | |||
| \U | |||
| Uppercase till \E (think vi) | |||
| (?=pattern) | |||
| Zero-width positive look-ahead assertions. | |||
| (?!pattern) | |||
| Zero-width negative look-ahead assertions. | |||
| (?<=pattern) | |||
| Zero-width positive look-behind assertions. | |||
| (?<!pattern) | |||
| Zero-width negative look-behind assertions. | |||
| Documentation especially for the nonstandard features of TRE, such | |||
| as approximate matching, is a work in progress (with "progress" | |||
| loosely defined...) | |||
| Mailing lists | |||
| tre-general@lists.laurikari.net | |||
| This list is for any discussion on the TRE software, including | |||
| reporting bugs, feature requests, requests for help, and other | |||
| things. | |||
| tre-announce@lists.laurikari.net | |||
| Subscribe to this list to get announcements of new releases of | |||
| TRE. Alternatively, you can subscribe to the freshmeat.net | |||
| project and get similar announcements that way, if you prefer. | |||
| Ville Laurikari <vl@iki.fi> | |||
| @@ -0,0 +1,29 @@ | |||
| Acknowledgements | |||
| Thanks for suggestions, interesting discussions, spotting bugs, | |||
| patches, and contributions (in alphabetical order): | |||
| Matthew Berg <galt@gothpoodle.com> | |||
| Angelo Borsotti <angelo.borsotti@alcatel.it> | |||
| Bob Carlitz <bob@info-ren.org> | |||
| Alistair Crooks <agc@pkgsrc.org> | |||
| Claude Devis <devis@tedm.ucl.ac.be> (UCL/CENTAL) | |||
| Rich Felker <dalias@aerifal.cx> | |||
| Glenn Fowler <gsf@research.att.com> | |||
| Peter D. Gray <pdg@uow.edu.au> | |||
| George Harpur <gfh@neurascript.com> | |||
| Jan Kasprzak <kas@fi.muni.cz> | |||
| Matthias Kilian <kili@outback.escape.de> | |||
| Rune Kleveland <runekl@opoint.com> | |||
| Rici Lake <RLake@oxfam.org.uk> | |||
| Bram Matthys <syzop@vulnscan.org> | |||
| Dominick Meglio <codemstr@ptd.net> | |||
| Aymeric Moizard <jack@atosc.org> | |||
| Daniel Nylander <po@danielnylander.se> | |||
| William J Poser <wjposer@ldc.upenn.edu> | |||
| Nikolai Saoukh <nms+python@otdel1.org> | |||
| Santiago Vila <sanvila@unex.es> | |||
| Nikolai Weibull <nikolai@bitwi.se> | |||
| Bill Yerazunis <wsy@merl.com> | |||
| @@ -0,0 +1,50 @@ | |||
| TODO: | |||
| * Documentation | |||
| - Finish the reference manual of the API. | |||
| - Finish the manual describing the syntax and semantics of regexps. | |||
| - Write a description of the algorithms used. There's already my | |||
| Master's Thesis, but it's not TRE-specific, and it's a | |||
| thesis, not an algorithm description. | |||
| - Write man page for tre regexp syntax. | |||
| * POSIX required features | |||
| - Support for collating elements and equivalence classes. This | |||
| requires some level of integration with libc. | |||
| * New features | |||
| - Support for GNU regex extensions. | |||
| - word boundary syntax [[:<:]] and [[:>:]] | |||
| - beginning and end of buffer assertions ("\`" and "\'") | |||
| - is there something else missing? | |||
| - Better system ABI support for non-glibc systems? | |||
| - Transposition operation for the approximate matcher? | |||
| * Extend API | |||
| - Real-time interface? | |||
| - design API | |||
| - return if not finished after a certain amount of work | |||
| - easy for regexec(), more work for regcomp(). | |||
| * Optimizations | |||
| - Make specialized versions of matcher loops for REG_NOSUB. | |||
| - Find out the longest string that must occur in any match, and | |||
| search for it first (with a fast Boyer-Moore search, or maybe | |||
| just strstr). Then match both ways to see if it was part of | |||
| match. | |||
| - Some kind of a pessimistic histogram filter might speed up | |||
| searching for approximate matching. | |||
| - Optimize tre_tnfa_run_parallel to be faster (swap instead of | |||
| copying everything? Assembler optimizations?) | |||
| - Write a benchmark suite to see whan effects different | |||
| optimizations have in different situations. | |||
| @@ -0,0 +1,258 @@ | |||
| /* config.h.in. Generated from configure.ac by autoheader. */ | |||
| /* Define to one of `_getb67', `GETB67', `getb67' for Cray-2 and Cray-YMP | |||
| systems. This function is required for `alloca.c' support on those systems. | |||
| */ | |||
| #undef CRAY_STACKSEG_END | |||
| /* Define to 1 if using `alloca.c'. */ | |||
| #undef C_ALLOCA | |||
| /* Define to 1 if translation of program messages to the user's native | |||
| language is requested. */ | |||
| #undef ENABLE_NLS | |||
| /* Define to 1 if you have `alloca', as a function or macro. */ | |||
| #undef HAVE_ALLOCA | |||
| /* Define to 1 if you have <alloca.h> and it should be used (not on Ultrix). | |||
| */ | |||
| #undef HAVE_ALLOCA_H | |||
| /* Define to 1 if you have the MacOS X function CFLocaleCopyCurrent in the | |||
| CoreFoundation framework. */ | |||
| #undef HAVE_CFLOCALECOPYCURRENT | |||
| /* Define to 1 if you have the MacOS X function CFPreferencesCopyAppValue in | |||
| the CoreFoundation framework. */ | |||
| #undef HAVE_CFPREFERENCESCOPYAPPVALUE | |||
| /* Define if the GNU dcgettext() function is already present or preinstalled. | |||
| */ | |||
| #undef HAVE_DCGETTEXT | |||
| /* Define to 1 if you have the <dlfcn.h> header file. */ | |||
| #undef HAVE_DLFCN_H | |||
| /* Define to 1 if you have the <getopt.h> header file. */ | |||
| #undef HAVE_GETOPT_H | |||
| /* Define to 1 if you have the `getopt_long' function. */ | |||
| #undef HAVE_GETOPT_LONG | |||
| /* Define if the GNU gettext() function is already present or preinstalled. */ | |||
| #undef HAVE_GETTEXT | |||
| /* Define if you have the iconv() function and it works. */ | |||
| #undef HAVE_ICONV | |||
| /* Define to 1 if you have the <inttypes.h> header file. */ | |||
| #undef HAVE_INTTYPES_H | |||
| /* Define to 1 if you have the `isascii' function. */ | |||
| #undef HAVE_ISASCII | |||
| /* Define to 1 if you have the `isblank' function. */ | |||
| #undef HAVE_ISBLANK | |||
| /* Define to 1 if you have the `iswascii' function or macro. */ | |||
| #undef HAVE_ISWASCII | |||
| /* Define to 1 if you have the `iswblank' function or macro. */ | |||
| #undef HAVE_ISWBLANK | |||
| /* Define to 1 if you have the `iswctype' function or macro. */ | |||
| #undef HAVE_ISWCTYPE | |||
| /* Define to 1 if you have the `iswlower' function or macro. */ | |||
| #undef HAVE_ISWLOWER | |||
| /* Define to 1 if you have the `iswupper' function or macro. */ | |||
| #undef HAVE_ISWUPPER | |||
| /* Define to 1 if you have the <libutf8.h> header file. */ | |||
| #undef HAVE_LIBUTF8_H | |||
| /* Define to 1 if you have the `mbrtowc' function or macro. */ | |||
| #undef HAVE_MBRTOWC | |||
| /* Define to 1 if the system has the type `mbstate_t'. */ | |||
| #undef HAVE_MBSTATE_T | |||
| /* Define to 1 if you have the `mbtowc' function or macro. */ | |||
| #undef HAVE_MBTOWC | |||
| /* Define to 1 if you have the <memory.h> header file. */ | |||
| #undef HAVE_MEMORY_H | |||
| /* Define to 1 if you have the <regex.h> header file. */ | |||
| #undef HAVE_REGEX_H | |||
| /* Define to 1 if the system has the type `reg_errcode_t'. */ | |||
| #undef HAVE_REG_ERRCODE_T | |||
| /* Define to 1 if you have the <stdint.h> header file. */ | |||
| #undef HAVE_STDINT_H | |||
| /* Define to 1 if you have the <stdlib.h> header file. */ | |||
| #undef HAVE_STDLIB_H | |||
| /* Define to 1 if you have the <strings.h> header file. */ | |||
| #undef HAVE_STRINGS_H | |||
| /* Define to 1 if you have the <string.h> header file. */ | |||
| #undef HAVE_STRING_H | |||
| /* Define to 1 if you have the <sys/stat.h> header file. */ | |||
| #undef HAVE_SYS_STAT_H | |||
| /* Define to 1 if you have the <sys/types.h> header file. */ | |||
| #undef HAVE_SYS_TYPES_H | |||
| /* Define to 1 if you have the `towlower' function or macro. */ | |||
| #undef HAVE_TOWLOWER | |||
| /* Define to 1 if you have the `towupper' function or macro. */ | |||
| #undef HAVE_TOWUPPER | |||
| /* Define to 1 if you have the <unistd.h> header file. */ | |||
| #undef HAVE_UNISTD_H | |||
| /* Define to 1 if you have the <wchar.h> header file. */ | |||
| #undef HAVE_WCHAR_H | |||
| /* Define to 1 if the system has the type `wchar_t'. */ | |||
| #undef HAVE_WCHAR_T | |||
| /* Define to 1 if you have the `wcschr' function or macro. */ | |||
| #undef HAVE_WCSCHR | |||
| /* Define to 1 if you have the `wcscpy' function or macro. */ | |||
| #undef HAVE_WCSCPY | |||
| /* Define to 1 if you have the `wcslen' function or macro. */ | |||
| #undef HAVE_WCSLEN | |||
| /* Define to 1 if you have the `wcsncpy' function or macro. */ | |||
| #undef HAVE_WCSNCPY | |||
| /* Define to 1 if you have the `wcsrtombs' function or macro. */ | |||
| #undef HAVE_WCSRTOMBS | |||
| /* Define to 1 if you have the `wcstombs' function or macro. */ | |||
| #undef HAVE_WCSTOMBS | |||
| /* Define to 1 if you have the `wctype' function or macro. */ | |||
| #undef HAVE_WCTYPE | |||
| /* Define to 1 if you have the <wctype.h> header file. */ | |||
| #undef HAVE_WCTYPE_H | |||
| /* Define to 1 if the system has the type `wint_t'. */ | |||
| #undef HAVE_WINT_T | |||
| /* Define if you want to disable debug assertions. */ | |||
| #undef NDEBUG | |||
| /* Define to 1 if your C compiler doesn't accept -c and -o together. */ | |||
| #undef NO_MINUS_C_MINUS_O | |||
| /* Name of package */ | |||
| #undef PACKAGE | |||
| /* Define to the address where bug reports for this package should be sent. */ | |||
| #undef PACKAGE_BUGREPORT | |||
| /* Define to the full name of this package. */ | |||
| #undef PACKAGE_NAME | |||
| /* Define to the full name and version of this package. */ | |||
| #undef PACKAGE_STRING | |||
| /* Define to the one symbol short name of this package. */ | |||
| #undef PACKAGE_TARNAME | |||
| /* Define to the version of this package. */ | |||
| #undef PACKAGE_VERSION | |||
| /* If using the C implementation of alloca, define if you know the | |||
| direction of stack growth for your system; otherwise it will be | |||
| automatically deduced at runtime. | |||
| STACK_DIRECTION > 0 => grows toward higher addresses | |||
| STACK_DIRECTION < 0 => grows toward lower addresses | |||
| STACK_DIRECTION = 0 => direction of growth unknown */ | |||
| #undef STACK_DIRECTION | |||
| /* Define to 1 if you have the ANSI C header files. */ | |||
| #undef STDC_HEADERS | |||
| /* Define if you want to enable approximate matching functionality. */ | |||
| #undef TRE_APPROX | |||
| /* Define if you want TRE to print debug messages to stdout. */ | |||
| #undef TRE_DEBUG | |||
| /* Define to enable multibyte character set support. */ | |||
| #undef TRE_MULTIBYTE | |||
| /* Define to a field in the regex_t struct where TRE should store a pointer to | |||
| the internal tre_tnfa_t structure */ | |||
| #undef TRE_REGEX_T_FIELD | |||
| /* Define to the absolute path to the system regex.h */ | |||
| #undef TRE_SYSTEM_REGEX_H_PATH | |||
| /* Define if you want TRE to use alloca() instead of malloc() when allocating | |||
| memory needed for regexec operations. */ | |||
| #undef TRE_USE_ALLOCA | |||
| /* Define to include the system regex.h from TRE regex.h */ | |||
| #undef TRE_USE_SYSTEM_REGEX_H | |||
| /* TRE version string. */ | |||
| #undef TRE_VERSION | |||
| /* TRE version level 1. */ | |||
| #undef TRE_VERSION_1 | |||
| /* TRE version level 2. */ | |||
| #undef TRE_VERSION_2 | |||
| /* TRE version level 3. */ | |||
| #undef TRE_VERSION_3 | |||
| /* Define to enable wide character (wchar_t) support. */ | |||
| #undef TRE_WCHAR | |||
| /* Version number of package */ | |||
| #undef VERSION | |||
| /* Define to the maximum value of wchar_t if not already defined elsewhere */ | |||
| #undef WCHAR_MAX | |||
| /* Define if wchar_t is signed */ | |||
| #undef WCHAR_T_SIGNED | |||
| /* Define if wchar_t is unsigned */ | |||
| #undef WCHAR_T_UNSIGNED | |||
| /* Number of bits in a file offset, on hosts where this is settable. */ | |||
| #undef _FILE_OFFSET_BITS | |||
| /* Define to enable GNU extensions in glibc */ | |||
| #undef _GNU_SOURCE | |||
| /* Define for large files, on AIX-style hosts. */ | |||
| #undef _LARGE_FILES | |||
| /* Define on IRIX */ | |||
| #undef _REGCOMP_INTERNAL | |||
| /* Define to empty if `const' does not conform to ANSI C. */ | |||
| #undef const | |||
| /* Define to `__inline__' or `__inline' if that's what the C compiler | |||
| calls it, or to nothing if 'inline' is not supported under any name. */ | |||
| #ifndef __cplusplus | |||
| #undef inline | |||
| #endif | |||
| @@ -0,0 +1,571 @@ | |||
| dnl Process this file with autoconf to produce a configure script. | |||
| AC_INIT(TRE, 0.8.0, [tre-general@lists.laurikari.net]) | |||
| AC_CONFIG_SRCDIR([lib/regcomp.c]) | |||
| AC_CONFIG_AUX_DIR(utils) | |||
| AC_CANONICAL_TARGET | |||
| AM_INIT_AUTOMAKE(1.9.0) | |||
| AC_PREREQ(2.59) | |||
| AM_GNU_GETTEXT_VERSION(0.17) | |||
| dnl Checks for programs. | |||
| AC_PROG_CC | |||
| AC_PROG_CPP | |||
| AC_PROG_INSTALL | |||
| AM_PROG_CC_C_O | |||
| tre_version_1=`echo $PACKAGE_VERSION | cut -d . -f 1` | |||
| tre_version_2=`echo $PACKAGE_VERSION | cut -d . -f 2` | |||
| tre_version_3=`echo $PACKAGE_VERSION | cut -d . -f 3` | |||
| tre_version=$tre_version_1.$tre_version_2.$tre_version_3 | |||
| AC_DEFINE_UNQUOTED(TRE_VERSION, "$tre_version", [ TRE version string. ]) | |||
| AC_DEFINE_UNQUOTED(TRE_VERSION_1, $tre_version_1, [ TRE version level 1. ]) | |||
| AC_DEFINE_UNQUOTED(TRE_VERSION_2, $tre_version_2, [ TRE version level 2. ]) | |||
| AC_DEFINE_UNQUOTED(TRE_VERSION_3, $tre_version_3, [ TRE version level 3. ]) | |||
| AC_SUBST(TRE_VERSION, $tre_version) | |||
| dnl Options | |||
| AC_ARG_ENABLE(profile, | |||
| AC_HELP_STRING([--enable-profile], | |||
| [enable profiling with gprof @<:@default=disabled@:>@]), | |||
| [ tre_profile="$enableval" ], | |||
| [ tre_profile="no" ]) | |||
| AC_ARG_ENABLE(debug, | |||
| AC_HELP_STRING( | |||
| [--enable-debug], | |||
| [enable development-time debugging @<:@default=disabled@:>@]), | |||
| [ tre_debug="$enableval" ], | |||
| [ tre_debug="no" ]) | |||
| if test "$tre_debug" = "yes"; then | |||
| AM_CONDITIONAL(TRE_DEBUG, true) | |||
| AC_DEFINE(TRE_DEBUG, 1, | |||
| [ Define if you want TRE to print debug messages to stdout. ]) | |||
| else | |||
| AM_CONDITIONAL(TRE_DEBUG, false) | |||
| AC_DEFINE(NDEBUG, 1, [ Define if you want to disable debug assertions. ]) | |||
| fi | |||
| if test "$tre_profile" = "yes"; then | |||
| CFLAGS="$CFLAGS -pg" | |||
| AM_CONDITIONAL(TRE_PROFILE, true) | |||
| else | |||
| AM_CONDITIONAL(TRE_PROFILE, false) | |||
| fi | |||
| AC_ARG_ENABLE(warnings, | |||
| AC_HELP_STRING( | |||
| [--disable-warnings], | |||
| [disable C compiler warning messages @<:@default=enabled@:>@]), | |||
| [ tre_cc_warnings="$enableval" ], | |||
| [ tre_cc_warnings="yes" ]) | |||
| if test "$tre_cc_warnings" = "yes"; then | |||
| VL_PROG_CC_WARNINGS() | |||
| fi | |||
| AC_ARG_ENABLE(approx, | |||
| AC_HELP_STRING( | |||
| [--disable-approx], | |||
| [disable the approximate matching functionality @<:@default=enabled@:>@]), | |||
| [ tre_approx="$enableval" ], | |||
| [ tre_approx="yes" ]) | |||
| if test "$tre_approx" = "yes"; then | |||
| AC_DEFINE(TRE_APPROX, 1, | |||
| [ Define if you want to enable approximate matching functionality. ]) | |||
| AM_CONDITIONAL(TRE_APPROX, true) | |||
| else | |||
| AM_CONDITIONAL(TRE_APPROX, false) | |||
| fi | |||
| if test "$tre_approx" = "yes"; then | |||
| AC_ARG_ENABLE(agrep, | |||
| AC_HELP_STRING([--disable-agrep], | |||
| [Do not build and install the agrep tool @<:@default=install@:>@]), | |||
| [ tre_agrep="$enableval" ], | |||
| [ tre_agrep="yes" ]) | |||
| else | |||
| tre_agrep="no (requires approximate matching)" | |||
| fi | |||
| if test "$tre_agrep" = "yes"; then | |||
| AM_CONDITIONAL(TRE_AGREP, true) | |||
| else | |||
| AM_CONDITIONAL(TRE_AGREP, false) | |||
| fi | |||
| dnl Checks for compiler characteristics. | |||
| AC_C_CONST | |||
| AC_C_INLINE | |||
| dnl Checks for headers, functions, types, and macros | |||
| AC_DEFINE(_GNU_SOURCE, 1, [ Define to enable GNU extensions in glibc ]) | |||
| AC_HEADER_STDC | |||
| AC_ARG_WITH(alloca, | |||
| AC_HELP_STRING( | |||
| [--without-alloca], | |||
| [don't use alloca @<:@default=use@:>@]), | |||
| [ tre_use_alloca="$withval" ], | |||
| [ tre_use_alloca="yes" ]) | |||
| if test "$tre_use_alloca" = "yes"; then | |||
| ALLOCA="" | |||
| AC_FUNC_ALLOCA | |||
| if test -z "$ALLOCA"; then | |||
| # alloca() works. | |||
| AC_DEFINE(TRE_USE_ALLOCA, 1, | |||
| [ Define if you want TRE to use alloca() instead of malloc() when | |||
| allocating memory needed for regexec operations. ]) | |||
| fi | |||
| fi | |||
| AC_ARG_ENABLE(system-abi, | |||
| AC_HELP_STRING( | |||
| [--enable-system-abi], | |||
| [try to make TRE compatible with the system \ | |||
| regex ABI @<:@default=disabled@:>@]), | |||
| [ tre_system_abi="$enableval" ], | |||
| [ tre_system_abi="no" ]) | |||
| # If we are building a version compatible with the system ABI, we need to | |||
| # find an absolute path to the system regex.h (so it can be included from | |||
| # TRE regex.h using `#include "/path/to/regex.h"'). Then we need to | |||
| # find a field in the system defined regex_t struct where a pointer to | |||
| # the compiled regex object can be stored. | |||
| if test "$tre_system_abi" = "yes"; then | |||
| # Check that there is a system regex.h to begin with. We may need | |||
| # to include sys/types.h before regex.h, so check for that first. | |||
| AC_CHECK_HEADERS([sys/types.h]) | |||
| AC_CHECK_HEADERS([regex.h], [], | |||
| [ tre_system_abi="no (regex.h not found)" ], | |||
| [#if HAVE_SYS_TYPES_H | |||
| #include <sys/types.h> | |||
| #endif | |||
| ]) | |||
| fi | |||
| if test "$tre_system_abi" = "yes"; then | |||
| # Find out where system regex.h is. This is done by running the C | |||
| # preprocessor and grepping its output, hopefully getting a full | |||
| # path to regex.h. | |||
| AC_MSG_CHECKING([path to system regex.h]) | |||
| echo '#include <regex.h>' > conftest.c | |||
| tre_system_regex_h=`$CPP conftest.c \ | |||
| | grep '^#[a-z]* [0-9]* "\(.*regex.h\)"' \ | |||
| | head -1 \ | |||
| | sed 's/^#[a-z]* [0-9]* \"\(.*\)\".*/\1/'` | |||
| rm -f conftest.c | |||
| if test -n "$tre_system_regex_h" && test -f "$tre_system_regex_h"; then | |||
| AC_MSG_RESULT($tre_system_regex_h) | |||
| else | |||
| AC_MSG_RESULT(unknown) | |||
| tre_system_abi="no (could determine path to systeg regex.h)" | |||
| fi | |||
| fi | |||
| if test "$tre_system_abi" = "yes"; then | |||
| # Find a field in the system regex_t struct where we can store a pointer. | |||
| # This is done by trying several names that are known to work on different | |||
| # systems. | |||
| AC_MSG_CHECKING([for a usable field for a pointer in regex_t]) | |||
| tre_regex_t_field="" | |||
| for field in buffer re_comp __re_comp __reg_expression \ | |||
| re_g "re_pad@<:@0@:>@"; do | |||
| if test -z "$tre_regex_t_field"; then | |||
| AC_COMPILE_IFELSE( | |||
| [ AC_LANG_PROGRAM([ | |||
| #include <sys/types.h> | |||
| #include <regex.h> | |||
| ], | |||
| [ | |||
| regex_t foo; | |||
| void *bar = foo.$field; | |||
| foo.$field = bar; | |||
| ])], | |||
| [ AC_MSG_RESULT($field) | |||
| tre_regex_t_field="$field" ]) | |||
| fi | |||
| done | |||
| if test -z "$tre_regex_t_field"; then | |||
| AC_MSG_RESULT(no) | |||
| tre_system_abi="no (unknown regex_t contents, report to \ | |||
| $PACKAGE_BUGREPORT)" | |||
| fi | |||
| fi | |||
| if test "$tre_system_abi" = "yes"; then | |||
| # So far, so good. Now check if we can redefine the system regex | |||
| # functions. For example, the system headers may define the | |||
| # standard functions as static wrapper functions (like on IRIX) | |||
| # which prevents redefining them later. | |||
| # IRIX has some macro magic which we need to turn off. | |||
| AC_DEFINE(_REGCOMP_INTERNAL, 1, [ Define on IRIX ]) | |||
| AC_MSG_CHECKING([if POSIX regex functions can be redefined]) | |||
| AC_COMPILE_IFELSE( | |||
| [ AC_LANG_PROGRAM([ | |||
| #include <sys/types.h> | |||
| #include <regex.h> | |||
| int | |||
| regcomp(regex_t *preg, const char *regex, int cflags) | |||
| { | |||
| return 0; | |||
| } | |||
| void | |||
| regfree(regex_t *preg) | |||
| { | |||
| return; | |||
| } | |||
| int | |||
| regexec(const regex_t *preg, const char *str, | |||
| size_t nmatch, regmatch_t pmatch@<:@@:>@, int eflags) | |||
| { | |||
| return 0; | |||
| } | |||
| size_t | |||
| regerror(int errcode, const regex_t *preg, char *errbuf, | |||
| size_t errbuf_size) | |||
| { | |||
| return 0; | |||
| } | |||
| ])], | |||
| [ AC_MSG_RESULT(yes) | |||
| tre_system_abi="yes" ], | |||
| [ AC_MSG_RESULT(no) | |||
| tre_system_abi="no (unable to redefine system functions)" ]) | |||
| fi | |||
| if test "$tre_system_abi" = "yes"; then | |||
| # Great, everything seems to be OK for ABI compatibility. Just check | |||
| # some additional types that may or may not be defined, and set up | |||
| # variables to enable ABI compatibility in regex.h. | |||
| AC_CHECK_TYPES([reg_errcode_t],,,[ | |||
| #ifdef HAVE_SYS_TYPES_H | |||
| #include <sys/types.h> | |||
| #endif /* HAVE_SYS_TYPES_H */ | |||
| #ifdef HAVE_REGEX_H | |||
| #include <regex.h> | |||
| #endif /* HAVE_REGEX_H */ | |||
| ]) | |||
| AC_DEFINE(TRE_USE_SYSTEM_REGEX_H, 1, | |||
| [ Define to include the system regex.h from TRE regex.h ]) | |||
| AC_DEFINE_UNQUOTED(TRE_SYSTEM_REGEX_H_PATH, "$tre_system_regex_h", | |||
| [ Define to the absolute path to the system regex.h ]) | |||
| AC_DEFINE_UNQUOTED(TRE_REGEX_T_FIELD, $tre_regex_t_field, | |||
| [ Define to a field in the regex_t struct where TRE should store a | |||
| pointer to the internal tre_tnfa_t structure ]) | |||
| else | |||
| AC_DEFINE(TRE_REGEX_T_FIELD, value) | |||
| fi | |||
| AC_CHECK_FUNCS([isascii isblank]) | |||
| AC_CHECK_HEADERS([getopt.h]) | |||
| AC_CHECK_FUNCS([getopt_long],, | |||
| [ # FreeBSD has a "gnugetopt" library. | |||
| AC_CHECK_LIB([gnugetopt], [getopt_long], | |||
| [ AC_DEFINE([HAVE_GETOPT_LONG]) ]) ]) | |||
| dnl Check whether wide character support should be enabled. | |||
| AC_ARG_ENABLE(wchar, | |||
| AC_HELP_STRING( | |||
| [--disable-wchar], | |||
| [disable the wide character (wchar_t) support @<:@default=detect@:>@]), | |||
| [ tre_enable_wchar="$enableval" ], | |||
| [ tre_enable_wchar="detect" ]) | |||
| dnl Check whether libutf8 location has been given. | |||
| AC_ARG_WITH(libutf8, | |||
| AC_HELP_STRING( | |||
| [--with-libutf8@<:@=DIR@:>@], | |||
| [search for libutf8 from DIR/include and DIR/lib]) | |||
| AC_HELP_STRING( | |||
| [--without-libutf8], | |||
| [do not use libutf8 @<:@default=use if needed@:>@]), | |||
| [ if test "$with_val" = "no"; then | |||
| tre_libutf8="no" | |||
| else | |||
| tre_libutf8="yes" | |||
| tre_libutf8_dirs="$with_libutf8" | |||
| tre_libutf8_libs="-lutf8" | |||
| fi ], | |||
| [ tre_libutf8="detect" | |||
| tre_libutf8_dirs="none /usr /usr/local" | |||
| tre_libutf8_libs="none -lutf8" ]) | |||
| if test "$tre_enable_wchar" != "no"; then | |||
| dnl Wide character support is requested. Check if we need libutf8. | |||
| old_libs="$LIBS" | |||
| old_ldflags="$LDFLAGS" | |||
| old_cppflags="$CPPFLAGS" | |||
| if test "$tre_libutf8" != "no"; then | |||
| AC_MSG_CHECKING([for libutf8]) | |||
| found="no" | |||
| dnl Go through directories in $tre_libutf8_dirs for CPPFLAGS and LDFLAGS. | |||
| for try_dir in $tre_libutf8_dirs; do | |||
| if test "$try_dir" = "none"; then | |||
| LDFLAGS="$old_ldflags" | |||
| CPPFLAGS="$old_cppflags" | |||
| else | |||
| LDFLAGS="$old_ldflags -L$try_dir/lib" | |||
| CPPFLAGS="$old_cppflags -I$try_dir/include" | |||
| fi | |||
| dnl Go through libs in $tre_libutf8_libs. | |||
| for try_lib in $tre_libutf8_libs; do | |||
| if test "$try_lib" = "none"; then | |||
| LIBS="$old_libs" | |||
| else | |||
| LIBS="$try_lib $old_libs" | |||
| fi | |||
| dnl Check if mbrtowc or utf8_mbrtowc is available with the current | |||
| dnl CPPFLAGS, LDFLAGS, and LIBS. | |||
| AC_LINK_IFELSE([AC_LANG_CALL([],[mbrtowc])],[found="yes"]) | |||
| if test "$found" = "yes"; then | |||
| break; | |||
| fi | |||
| AC_LINK_IFELSE([AC_LANG_CALL([],[utf8_mbrtowc])],[found="yes"]) | |||
| if test "$found" = "yes"; then | |||
| break; | |||
| fi | |||
| done | |||
| if test "$found" = "yes"; then | |||
| break; | |||
| fi | |||
| done | |||
| dnl Report results. | |||
| if test "$found" = "yes"; then | |||
| if test "$LIBS" = "$old_libs"; then | |||
| AC_MSG_RESULT([not needed]) | |||
| tre_libutf8="no" | |||
| else | |||
| AC_MSG_RESULT([using from $try_dir/{lib,include}]) | |||
| tre_libutf8="yes" | |||
| fi | |||
| else | |||
| LIBS="$old_libs" | |||
| LDFLAGS="$old_ldflags" | |||
| CPPFLAGS="$old_cppflags" | |||
| if test "$tre_libutf8" = "detect"; then | |||
| AC_MSG_RESULT([no]) | |||
| tre_libutf8="no" | |||
| else | |||
| # Fail if libutf8 was requested but was not found. | |||
| AC_MSG_ERROR([not found]) | |||
| fi | |||
| fi | |||
| fi | |||
| if test "$tre_libutf8" = "yes"; then | |||
| dnl We do need libutf8, use the libutf8 headers. | |||
| tre_wchar="yes" | |||
| AC_CHECK_HEADERS([libutf8.h]) | |||
| else | |||
| dnl Use the POSIX headers. | |||
| AC_CHECK_HEADERS([wchar.h wctype.h]) | |||
| fi | |||
| else | |||
| tre_wchar_reason="disabled with --disable-wchar" | |||
| tre_wchar="no ($tre_wchar_reason)" | |||
| fi | |||
| tre_includes=" | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #ifdef HAVE_LIBUTF8_H | |||
| #include <libutf8.h> | |||
| #endif /* HAVE_LIBUTF8_H */ | |||
| " | |||
| if test "$tre_enable_wchar" != "no"; then | |||
| dnl We need wchar_t and WCHAR_MAX | |||
| AC_CHECK_TYPES([wchar_t], | |||
| [ tre_wchar="yes" | |||
| AX_DECL_WCHAR_MAX ], | |||
| [ tre_wchar_reason="wchar_t type not found" | |||
| tre_wchar="no ($tre_wchar_reason)" ], | |||
| [ $tre_includes ]) | |||
| if test "$tre_wchar" = "yes"; then | |||
| dnl We need wint_t | |||
| AC_CHECK_TYPES([wint_t],, | |||
| [ tre_wchar_reason="wint_t type not found" | |||
| tre_wchar="no ($tre_wchar_reason)" ], | |||
| [ $tre_includes ]) | |||
| fi | |||
| if test "$tre_wchar" = "yes"; then | |||
| dnl We may need mbstate_t | |||
| AC_CHECK_TYPES([mbstate_t],,,[ $tre_includes ]) | |||
| fi | |||
| if test "$tre_wchar" = "yes"; then | |||
| dnl We need either wcsrtombs (preferred) or wcstombs | |||
| found="no" | |||
| AX_CHECK_FUNCS_COMP([wcsrtombs wcstombs],[found="yes"; break],, | |||
| [$tre_includes]) | |||
| if test "$found" = "no"; then | |||
| tre_wchar_reason="no wcsrtombs or wcstombs found" | |||
| tre_wchar="no ($tre_wchar_reason)" | |||
| fi | |||
| fi | |||
| if test "$tre_wchar" = "yes"; then | |||
| dnl We need all these | |||
| AX_CHECK_FUNCS_COMP([iswlower iswupper towlower towupper wcschr \ | |||
| wcscpy wcslen wcsncpy], | |||
| [ tre_wchar="yes" ], | |||
| [ tre_wchar_reason="$ac_func not found" | |||
| tre_wchar="no ($tre_wchar_reason)" | |||
| break ], | |||
| [ $tre_includes ]) | |||
| fi | |||
| fi | |||
| case $host in | |||
| *-mingw*) | |||
| dnl wcsrtombs and wcstombs don't seem to work at all on MinGW. | |||
| if test "$tre_libutf8" != "yes"; then | |||
| tre_wchar_reason="Not supported on MinGW" | |||
| tre_wchar="no ($tre_wchar_reason)" | |||
| fi | |||
| ;; | |||
| esac | |||
| # Fail if wide character support was specifically requested but is | |||
| # not supported on this system. | |||
| if test "$tre_enable_wchar" = "yes"; then | |||
| if test "$tre_wchar" != "yes"; then | |||
| AC_MSG_ERROR([Cannot enable wide character support: $tre_wchar_reason]) | |||
| fi | |||
| fi | |||
| if test "$tre_wchar" = "yes"; then | |||
| AC_DEFINE(TRE_WCHAR, 1, | |||
| [ Define to enable wide character (wchar_t) support. ]) | |||
| dnl We make use of these if they exist. | |||
| AX_CHECK_FUNCS_COMP([wctype iswctype],,,[$tre_includes]) | |||
| AX_CHECK_FUNCS_COMP([iswascii iswblank],,,[$tre_includes]) | |||
| fi | |||
| dnl Check for multibyte character set support | |||
| AC_ARG_ENABLE(multibyte, | |||
| AC_HELP_STRING( | |||
| [--disable-multibyte], | |||
| [disable multibyte character set support @<:@default=detect@:>@]), | |||
| [ tre_enable_multibyte="$enableval" ], | |||
| [ tre_enable_multibyte="detect" ]) | |||
| dnl Wide character support is required for multibyte character set support | |||
| if test "$tre_wchar" != "yes"; then | |||
| if test "$tre_enable_multibyte" = "yes"; then | |||
| AC_MSG_ERROR([Cannot enable multibyte character support because wide \ | |||
| character support is not enabled ($tre_wchar_reason)]) | |||
| fi | |||
| fi | |||
| if test "$tre_enable_multibyte" != "no"; then | |||
| if test "$tre_wchar" != "yes"; then | |||
| tre_multibyte="no (requires wide character support)" | |||
| else | |||
| found="no" | |||
| dnl We need either mbrtowc (preferred) or mbtowc | |||
| AX_CHECK_FUNCS_COMP([mbrtowc mbtowc],[found="yes"; break],,[$tre_includes]) | |||
| if test "$found" = "no"; then | |||
| tre_mbs_reason="no mbrtowc or mbtowc found" | |||
| tre_multibyte="no ($tre_mbs_reason)" | |||
| else | |||
| tre_multibyte="yes" | |||
| fi | |||
| fi | |||
| else | |||
| tre_multibyte="no (disabled with --disable-multibyte)" | |||
| fi | |||
| # Fail if multibyte character set support was specifically requested but | |||
| # is not supported on this system. | |||
| if test "$tre_enable_multibyte" = "yes"; then | |||
| if test "$tre_multibyte" != "yes"; then | |||
| AC_MSG_ERROR([Cannot enable multibyte character set support: \ | |||
| $tre_mbs_reason]) | |||
| fi | |||
| fi | |||
| if test "$tre_multibyte" = "yes"; then | |||
| AM_CONDITIONAL(TRE_MULTIBYTE, true) | |||
| AC_DEFINE(TRE_MULTIBYTE, 1, | |||
| [ Define to enable multibyte character set support. ]) | |||
| else | |||
| AM_CONDITIONAL(TRE_MULTIBYTE, false) | |||
| fi | |||
| AC_SYS_LARGEFILE | |||
| AM_GNU_GETTEXT([external]) | |||
| AC_LIBTOOL_TAGS([]) | |||
| AC_LIBTOOL_WIN32_DLL | |||
| AM_DISABLE_STATIC | |||
| AC_PROG_LIBTOOL | |||
| dnl Output files | |||
| AC_CONFIG_HEADERS([config.h lib/tre-config.h]) | |||
| AC_CONFIG_FILES([ | |||
| Makefile | |||
| doc/Makefile | |||
| doc/agrep.1 | |||
| lib/Makefile | |||
| m4/Makefile | |||
| po/Makefile.in | |||
| src/Makefile | |||
| tests/Makefile | |||
| tests/agrep/Makefile | |||
| tre.pc | |||
| tre.spec | |||
| utils/Makefile | |||
| ]) | |||
| AC_OUTPUT | |||
| dnl Print configuration summary | |||
| cat <<EOF | |||
| Configuration summary | |||
| ===================== | |||
| TRE is now configured as follows: | |||
| * Compilation environment | |||
| CC = $CC | |||
| CFLAGS = $CFLAGS | |||
| CPP = $CPP | |||
| CPPFLAGS = $CPPFLAGS | |||
| LD = $LD | |||
| LDFLAGS = $LDFLAGS | |||
| LIBS = $LIBS | |||
| Use alloca(): $tre_use_alloca | |||
| * TRE options | |||
| Development-time debugging: $tre_debug | |||
| System regex ABI compatibility: $tre_system_abi | |||
| Wide character (wchar_t) support: $tre_wchar | |||
| Multibyte character set support: $tre_multibyte | |||
| Approximate matching support: $tre_approx | |||
| Build and install agrep: $tre_agrep | |||
| EOF | |||
| @@ -0,0 +1,10 @@ | |||
| ## Process this file with automake to produce Makefile.in | |||
| man_MANS = agrep.1 | |||
| EXTRA_DIST = \ | |||
| agrep.1.in \ | |||
| tre-api.html \ | |||
| tre-syntax.html \ | |||
| default.css | |||
| @@ -0,0 +1,417 @@ | |||
| # Makefile.in generated by automake 1.10.1 from Makefile.am. | |||
| # @configure_input@ | |||
| # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, | |||
| # 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. | |||
| # This Makefile.in is free software; the Free Software Foundation | |||
| # gives unlimited permission to copy and/or distribute it, | |||
| # with or without modifications, as long as this notice is preserved. | |||
| # This program is distributed in the hope that it will be useful, | |||
| # but WITHOUT ANY WARRANTY, to the extent permitted by law; without | |||
| # even the implied warranty of MERCHANTABILITY or FITNESS FOR A | |||
| # PARTICULAR PURPOSE. | |||
| @SET_MAKE@ | |||
| VPATH = @srcdir@ | |||
| pkgdatadir = $(datadir)/@PACKAGE@ | |||
| pkglibdir = $(libdir)/@PACKAGE@ | |||
| pkgincludedir = $(includedir)/@PACKAGE@ | |||
| am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd | |||
| install_sh_DATA = $(install_sh) -c -m 644 | |||
| install_sh_PROGRAM = $(install_sh) -c | |||
| install_sh_SCRIPT = $(install_sh) -c | |||
| INSTALL_HEADER = $(INSTALL_DATA) | |||
| transform = $(program_transform_name) | |||
| NORMAL_INSTALL = : | |||
| PRE_INSTALL = : | |||
| POST_INSTALL = : | |||
| NORMAL_UNINSTALL = : | |||
| PRE_UNINSTALL = : | |||
| POST_UNINSTALL = : | |||
| build_triplet = @build@ | |||
| host_triplet = @host@ | |||
| target_triplet = @target@ | |||
| subdir = doc | |||
| DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ | |||
| $(srcdir)/agrep.1.in | |||
| ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 | |||
| am__aclocal_m4_deps = $(top_srcdir)/m4/ac_libtool_tags.m4 \ | |||
| $(top_srcdir)/m4/ax_check_funcs_comp.m4 \ | |||
| $(top_srcdir)/m4/ax_check_sign.m4 \ | |||
| $(top_srcdir)/m4/ax_decl_wchar_max.m4 \ | |||
| $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ | |||
| $(top_srcdir)/m4/intlmacosx.m4 $(top_srcdir)/m4/lib-ld.m4 \ | |||
| $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ | |||
| $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ | |||
| $(top_srcdir)/m4/progtest.m4 \ | |||
| $(top_srcdir)/m4/vl_prog_cc_warnings.m4 \ | |||
| $(top_srcdir)/configure.ac | |||
| am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ | |||
| $(ACLOCAL_M4) | |||
| mkinstalldirs = $(SHELL) $(top_srcdir)/utils/mkinstalldirs | |||
| CONFIG_HEADER = $(top_builddir)/config.h \ | |||
| $(top_builddir)/lib/tre-config.h | |||
| CONFIG_CLEAN_FILES = agrep.1 | |||
| SOURCES = | |||
| DIST_SOURCES = | |||
| man1dir = $(mandir)/man1 | |||
| am__installdirs = "$(DESTDIR)$(man1dir)" | |||
| NROFF = nroff | |||
| MANS = $(man_MANS) | |||
| DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) | |||
| ACLOCAL = @ACLOCAL@ | |||
| ALLOCA = @ALLOCA@ | |||
| AMTAR = @AMTAR@ | |||
| AR = @AR@ | |||
| AS = @AS@ | |||
| AUTOCONF = @AUTOCONF@ | |||
| AUTOHEADER = @AUTOHEADER@ | |||
| AUTOMAKE = @AUTOMAKE@ | |||
| AWK = @AWK@ | |||
| CC = @CC@ | |||
| CCDEPMODE = @CCDEPMODE@ | |||
| CFLAGS = @CFLAGS@ | |||
| CPP = @CPP@ | |||
| CPPFLAGS = @CPPFLAGS@ | |||
| CYGPATH_W = @CYGPATH_W@ | |||
| DEFS = @DEFS@ | |||
| DEPDIR = @DEPDIR@ | |||
| DLLTOOL = @DLLTOOL@ | |||
| DSYMUTIL = @DSYMUTIL@ | |||
| ECHO = @ECHO@ | |||
| ECHO_C = @ECHO_C@ | |||
| ECHO_N = @ECHO_N@ | |||
| ECHO_T = @ECHO_T@ | |||
| EGREP = @EGREP@ | |||
| EXEEXT = @EXEEXT@ | |||
| GETTEXT_MACRO_VERSION = @GETTEXT_MACRO_VERSION@ | |||
| GMSGFMT = @GMSGFMT@ | |||
| GMSGFMT_015 = @GMSGFMT_015@ | |||
| GREP = @GREP@ | |||
| INSTALL = @INSTALL@ | |||
| INSTALL_DATA = @INSTALL_DATA@ | |||
| INSTALL_PROGRAM = @INSTALL_PROGRAM@ | |||
| INSTALL_SCRIPT = @INSTALL_SCRIPT@ | |||
| INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ | |||
| INTLLIBS = @INTLLIBS@ | |||
| INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ | |||
| LDFLAGS = @LDFLAGS@ | |||
| LIBICONV = @LIBICONV@ | |||
| LIBINTL = @LIBINTL@ | |||
| LIBOBJS = @LIBOBJS@ | |||
| LIBS = @LIBS@ | |||
| LIBTOOL = @LIBTOOL@ | |||
| LN_S = @LN_S@ | |||
| LTLIBICONV = @LTLIBICONV@ | |||
| LTLIBINTL = @LTLIBINTL@ | |||
| LTLIBOBJS = @LTLIBOBJS@ | |||
| MAKEINFO = @MAKEINFO@ | |||
| MKDIR_P = @MKDIR_P@ | |||
| MSGFMT = @MSGFMT@ | |||
| MSGFMT_015 = @MSGFMT_015@ | |||
| MSGMERGE = @MSGMERGE@ | |||
| NMEDIT = @NMEDIT@ | |||
| OBJDUMP = @OBJDUMP@ | |||
| OBJEXT = @OBJEXT@ | |||
| PACKAGE = @PACKAGE@ | |||
| PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ | |||
| PACKAGE_NAME = @PACKAGE_NAME@ | |||
| PACKAGE_STRING = @PACKAGE_STRING@ | |||
| PACKAGE_TARNAME = @PACKAGE_TARNAME@ | |||
| PACKAGE_VERSION = @PACKAGE_VERSION@ | |||
| PATH_SEPARATOR = @PATH_SEPARATOR@ | |||
| POSUB = @POSUB@ | |||
| RANLIB = @RANLIB@ | |||
| SED = @SED@ | |||
| SET_MAKE = @SET_MAKE@ | |||
| SHELL = @SHELL@ | |||
| STRIP = @STRIP@ | |||
| TRE_VERSION = @TRE_VERSION@ | |||
| USE_NLS = @USE_NLS@ | |||
| VERSION = @VERSION@ | |||
| XGETTEXT = @XGETTEXT@ | |||
| XGETTEXT_015 = @XGETTEXT_015@ | |||
| XGETTEXT_EXTRA_OPTIONS = @XGETTEXT_EXTRA_OPTIONS@ | |||
| abs_builddir = @abs_builddir@ | |||
| abs_srcdir = @abs_srcdir@ | |||
| abs_top_builddir = @abs_top_builddir@ | |||
| abs_top_srcdir = @abs_top_srcdir@ | |||
| ac_ct_CC = @ac_ct_CC@ | |||
| am__include = @am__include@ | |||
| am__leading_dot = @am__leading_dot@ | |||
| am__quote = @am__quote@ | |||
| am__tar = @am__tar@ | |||
| am__untar = @am__untar@ | |||
| bindir = @bindir@ | |||
| build = @build@ | |||
| build_alias = @build_alias@ | |||
| build_cpu = @build_cpu@ | |||
| build_os = @build_os@ | |||
| build_vendor = @build_vendor@ | |||
| builddir = @builddir@ | |||
| datadir = @datadir@ | |||
| datarootdir = @datarootdir@ | |||
| docdir = @docdir@ | |||
| dvidir = @dvidir@ | |||
| exec_prefix = @exec_prefix@ | |||
| host = @host@ | |||
| host_alias = @host_alias@ | |||
| host_cpu = @host_cpu@ | |||
| host_os = @host_os@ | |||
| host_vendor = @host_vendor@ | |||
| htmldir = @htmldir@ | |||
| includedir = @includedir@ | |||
| infodir = @infodir@ | |||
| install_sh = @install_sh@ | |||
| libdir = @libdir@ | |||
| libexecdir = @libexecdir@ | |||
| localedir = @localedir@ | |||
| localstatedir = @localstatedir@ | |||
| mandir = @mandir@ | |||
| mkdir_p = @mkdir_p@ | |||
| oldincludedir = @oldincludedir@ | |||
| pdfdir = @pdfdir@ | |||
| prefix = @prefix@ | |||
| program_transform_name = @program_transform_name@ | |||
| psdir = @psdir@ | |||
| sbindir = @sbindir@ | |||
| sharedstatedir = @sharedstatedir@ | |||
| srcdir = @srcdir@ | |||
| sysconfdir = @sysconfdir@ | |||
| target = @target@ | |||
| target_alias = @target_alias@ | |||
| target_cpu = @target_cpu@ | |||
| target_os = @target_os@ | |||
| target_vendor = @target_vendor@ | |||
| top_builddir = @top_builddir@ | |||
| top_srcdir = @top_srcdir@ | |||
| man_MANS = agrep.1 | |||
| EXTRA_DIST = \ | |||
| agrep.1.in \ | |||
| tre-api.html \ | |||
| tre-syntax.html \ | |||
| default.css | |||
| all: all-am | |||
| .SUFFIXES: | |||
| $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) | |||
| @for dep in $?; do \ | |||
| case '$(am__configure_deps)' in \ | |||
| *$$dep*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ | |||
| && exit 0; \ | |||
| exit 1;; \ | |||
| esac; \ | |||
| done; \ | |||
| echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign doc/Makefile'; \ | |||
| cd $(top_srcdir) && \ | |||
| $(AUTOMAKE) --foreign doc/Makefile | |||
| .PRECIOUS: Makefile | |||
| Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status | |||
| @case '$?' in \ | |||
| *config.status*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ | |||
| *) \ | |||
| echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ | |||
| cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ | |||
| esac; | |||
| $(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(top_srcdir)/configure: $(am__configure_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(ACLOCAL_M4): $(am__aclocal_m4_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| agrep.1: $(top_builddir)/config.status $(srcdir)/agrep.1.in | |||
| cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ | |||
| mostlyclean-libtool: | |||
| -rm -f *.lo | |||
| clean-libtool: | |||
| -rm -rf .libs _libs | |||
| install-man1: $(man1_MANS) $(man_MANS) | |||
| @$(NORMAL_INSTALL) | |||
| test -z "$(man1dir)" || $(MKDIR_P) "$(DESTDIR)$(man1dir)" | |||
| @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ | |||
| l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ | |||
| for i in $$l2; do \ | |||
| case "$$i" in \ | |||
| *.1*) list="$$list $$i" ;; \ | |||
| esac; \ | |||
| done; \ | |||
| for i in $$list; do \ | |||
| if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ | |||
| else file=$$i; fi; \ | |||
| ext=`echo $$i | sed -e 's/^.*\\.//'`; \ | |||
| case "$$ext" in \ | |||
| 1*) ;; \ | |||
| *) ext='1' ;; \ | |||
| esac; \ | |||
| inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ | |||
| inst=`echo $$inst | sed -e 's/^.*\///'`; \ | |||
| inst=`echo $$inst | sed '$(transform)'`.$$ext; \ | |||
| echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ | |||
| $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst"; \ | |||
| done | |||
| uninstall-man1: | |||
| @$(NORMAL_UNINSTALL) | |||
| @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ | |||
| l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ | |||
| for i in $$l2; do \ | |||
| case "$$i" in \ | |||
| *.1*) list="$$list $$i" ;; \ | |||
| esac; \ | |||
| done; \ | |||
| for i in $$list; do \ | |||
| ext=`echo $$i | sed -e 's/^.*\\.//'`; \ | |||
| case "$$ext" in \ | |||
| 1*) ;; \ | |||
| *) ext='1' ;; \ | |||
| esac; \ | |||
| inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ | |||
| inst=`echo $$inst | sed -e 's/^.*\///'`; \ | |||
| inst=`echo $$inst | sed '$(transform)'`.$$ext; \ | |||
| echo " rm -f '$(DESTDIR)$(man1dir)/$$inst'"; \ | |||
| rm -f "$(DESTDIR)$(man1dir)/$$inst"; \ | |||
| done | |||
| tags: TAGS | |||
| TAGS: | |||
| ctags: CTAGS | |||
| CTAGS: | |||
| distdir: $(DISTFILES) | |||
| @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| list='$(DISTFILES)'; \ | |||
| dist_files=`for file in $$list; do echo $$file; done | \ | |||
| sed -e "s|^$$srcdirstrip/||;t" \ | |||
| -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ | |||
| case $$dist_files in \ | |||
| */*) $(MKDIR_P) `echo "$$dist_files" | \ | |||
| sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ | |||
| sort -u` ;; \ | |||
| esac; \ | |||
| for file in $$dist_files; do \ | |||
| if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ | |||
| if test -d $$d/$$file; then \ | |||
| dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ | |||
| if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ | |||
| cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ | |||
| fi; \ | |||
| cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ | |||
| else \ | |||
| test -f $(distdir)/$$file \ | |||
| || cp -p $$d/$$file $(distdir)/$$file \ | |||
| || exit 1; \ | |||
| fi; \ | |||
| done | |||
| check-am: all-am | |||
| check: check-am | |||
| all-am: Makefile $(MANS) | |||
| installdirs: | |||
| for dir in "$(DESTDIR)$(man1dir)"; do \ | |||
| test -z "$$dir" || $(MKDIR_P) "$$dir"; \ | |||
| done | |||
| install: install-am | |||
| install-exec: install-exec-am | |||
| install-data: install-data-am | |||
| uninstall: uninstall-am | |||
| install-am: all-am | |||
| @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am | |||
| installcheck: installcheck-am | |||
| install-strip: | |||
| $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ | |||
| install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ | |||
| `test -z '$(STRIP)' || \ | |||
| echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install | |||
| mostlyclean-generic: | |||
| clean-generic: | |||
| distclean-generic: | |||
| -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) | |||
| maintainer-clean-generic: | |||
| @echo "This command is intended for maintainers to use" | |||
| @echo "it deletes files that may require special tools to rebuild." | |||
| clean: clean-am | |||
| clean-am: clean-generic clean-libtool mostlyclean-am | |||
| distclean: distclean-am | |||
| -rm -f Makefile | |||
| distclean-am: clean-am distclean-generic | |||
| dvi: dvi-am | |||
| dvi-am: | |||
| html: html-am | |||
| info: info-am | |||
| info-am: | |||
| install-data-am: install-man | |||
| install-dvi: install-dvi-am | |||
| install-exec-am: | |||
| install-html: install-html-am | |||
| install-info: install-info-am | |||
| install-man: install-man1 | |||
| install-pdf: install-pdf-am | |||
| install-ps: install-ps-am | |||
| installcheck-am: | |||
| maintainer-clean: maintainer-clean-am | |||
| -rm -f Makefile | |||
| maintainer-clean-am: distclean-am maintainer-clean-generic | |||
| mostlyclean: mostlyclean-am | |||
| mostlyclean-am: mostlyclean-generic mostlyclean-libtool | |||
| pdf: pdf-am | |||
| pdf-am: | |||
| ps: ps-am | |||
| ps-am: | |||
| uninstall-am: uninstall-man | |||
| uninstall-man: uninstall-man1 | |||
| .MAKE: install-am install-strip | |||
| .PHONY: all all-am check check-am clean clean-generic clean-libtool \ | |||
| distclean distclean-generic distclean-libtool distdir dvi \ | |||
| dvi-am html html-am info info-am install install-am \ | |||
| install-data install-data-am install-dvi install-dvi-am \ | |||
| install-exec install-exec-am install-html install-html-am \ | |||
| install-info install-info-am install-man install-man1 \ | |||
| install-pdf install-pdf-am install-ps install-ps-am \ | |||
| install-strip installcheck installcheck-am installdirs \ | |||
| maintainer-clean maintainer-clean-generic mostlyclean \ | |||
| mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ | |||
| uninstall uninstall-am uninstall-man uninstall-man1 | |||
| # Tell versions [3.59,3.63) of GNU make to not export all variables. | |||
| # Otherwise a system limit (for SysV at least) may be exceeded. | |||
| .NOEXPORT: | |||
| @@ -0,0 +1,183 @@ | |||
| .TH agrep 1 "November 21, 2004" "TRE agrep @PACKAGE_VERSION@" | |||
| .SH NAME | |||
| agrep \- print lines approximately matching a pattern | |||
| .SH SYNOPSIS | |||
| .B agrep | |||
| .RI [ OPTION ]... | |||
| .I PATTERN | |||
| .RI [ FILE ]... | |||
| .SH DESCRIPTION | |||
| Searches for approximate matches of PATTERN in each FILE or standard | |||
| input. Example: `agrep \-2 optimize foo.txt' outputs all lines in | |||
| file `foo.txt' that match "optimize" within two errors. E.g. lines | |||
| which contain "optimise", "optmise", and "opitmize" all match. | |||
| .SH OPTIONS | |||
| .SS "Regexp selection and interpretation:" | |||
| .TP | |||
| .BI \-e " PATTERN" "\fR,\fP \-\^\-regexp=" PATTERN | |||
| Use | |||
| .I PATTERN | |||
| as a regular expression; useful to protect patterns beginning with | |||
| .BR \- . | |||
| .TP | |||
| .BR \-i ", " \-\^\-ignore\-case | |||
| Ignore case distinctions (as defined by the current locale) in | |||
| .I PATTERN | |||
| and input files. | |||
| .TP | |||
| .BR \-k ", " \-\^\-literal | |||
| Treat | |||
| .I PATTERN | |||
| as a literal string, that is, a fixed string with no special | |||
| characters. | |||
| .TP | |||
| .BR \-w ", " \-\^\-word\-regexp | |||
| Force | |||
| .I PATTERN | |||
| to match only whole words. A "whole word" is a substring which either | |||
| starts at the beginning or the record or is preceded by a non-word | |||
| constituent character. Similarly, the substring must either end at | |||
| the end of the record or be followed by a non-word constituent | |||
| character. Word-constituent characters are alphanumerics (as | |||
| defined by the current locale) and the underscore character. Note | |||
| that the non-word constituent characters | |||
| .B must | |||
| surround the match; they cannot be counted as errors. | |||
| .SS "Approximate matching settings:" | |||
| .TP | |||
| .BI \-D " NUM" "\fR,\fP \-\^\-delete\-cost=" NUM | |||
| Set cost of missing characters to | |||
| .IR NUM . | |||
| .TP | |||
| .BI \-I " NUM" "\fR,\fP \-\^\-insert\-cost=" NUM | |||
| Set cost of extra characters to | |||
| .IR NUM . | |||
| .TP | |||
| .BI \-S " NUM" "\fR,\fP \-\^\-substitute\-cost=" NUM | |||
| Set cost of incorrect characters to | |||
| .IR NUM . | |||
| Note that a deletion (a missing character) and an insertion (an extra | |||
| character) together constitute a substituted character, but the cost | |||
| will be the that of a deletion and an insertion added together. Thus, | |||
| if the const of a substitution is set to be larger than the sum | |||
| of the costs of deletion and insertion, direct substitutions will | |||
| never be done. | |||
| .TP | |||
| .BI \-E " NUM" "\fR,\fP \-\^\-max\-errors=" NUM | |||
| Select records that have at most | |||
| .I NUM | |||
| errors. | |||
| .TP | |||
| -\fI#\fR | |||
| Select records that have at most \fI#\fR errors (\fI#\fR is a | |||
| digit between 0 and 9). | |||
| .SS "Miscellaneous:" | |||
| .TP | |||
| .BI \-d " PATTERN" "\fR,\fP \-\^\-delimiter=" PATTERN | |||
| Set the record delimiter regular expression to | |||
| .IR PATTERN . | |||
| The text between two delimiters, before the first delimiter, and after | |||
| the last delimiter is considered to be a record. The default record | |||
| delimiter is the regexp "\\n", so by default a record is a line. | |||
| .I PATTERN | |||
| can be any regular expression that does not match the empty string. | |||
| For example, using | |||
| .B \-d | |||
| "^From " | |||
| defines mail messages as records in a Mailbox format file. | |||
| .TP | |||
| .BR \-v ", " \-\^\-invert\-match | |||
| Select non-matching records instead of matching records. | |||
| .TP | |||
| .BR \-V ", " \-\^\-version | |||
| Print version information and exit. | |||
| .TP | |||
| .BR \-y ", " \-\^\-nothing | |||
| Does nothing. This options exists only for compatibility with the | |||
| non-free agrep program. | |||
| .TP | |||
| .BR \-\^\-help | |||
| Display a brief help message and exit. | |||
| .SS "Output control:" | |||
| .TP | |||
| .BR \-B ", " \-\^\-best\-match | |||
| Only output the best matching records, that is, the records with the | |||
| lowest cost. This is currently implemented by making two passes over | |||
| the input files and cannot be used when reading from standard input. | |||
| .TP | |||
| .BR \-\^\-color ", " \-\^\-colour | |||
| Highlight the matching strings in the output with a color marker. The | |||
| color string is taken from the | |||
| .BI GREP_COLOR | |||
| environment variable. The default color is red. | |||
| .TP | |||
| .BR \-c ", " \-\^\-count | |||
| Only print a count of matching records per each input file, | |||
| suppressing normal output. | |||
| .TP | |||
| .BR \-h ", " \-\^\-no\-filename | |||
| Suppress the prefixing filename on output when multiple files are | |||
| searched. | |||
| .TP | |||
| .BR \-H ", " \-\^\-with\-filename | |||
| Prefix each output record with the name of the input file where the | |||
| record was read from. | |||
| .TP | |||
| .BR \-l ", " \-\^\-files\-with\-matches | |||
| Only print the name of each input file which contains at least one | |||
| match, suppressing normal output. The scanning for each file will | |||
| stop on the first match. | |||
| .TP | |||
| .BR \-n ", " \-\^\-record\-number | |||
| Prefix each output record with its sequence number in the input file. | |||
| The number of the first record is 1. | |||
| .TP | |||
| .BR \-q ", " \-\^\-quiet ", " \-\^\-silent | |||
| Do not write anything to standard output. Exit immediately with zero | |||
| exit status if a match is found. | |||
| .TP | |||
| .BR \-s ", " \-\^\-show\-cost | |||
| Print match cost with output. | |||
| .TP | |||
| .BR \-\^\-show\-position | |||
| Prefix each output record with the start and end offset of the first | |||
| match within the record. The offset of the first character of the | |||
| record is 0. The end position is given as the offset of the first | |||
| character after the match. | |||
| .TP | |||
| .BR \-M ", " \-\^\-delimiter\-after | |||
| By default, the record delimiter is the newline character and is | |||
| output after the matching record. If | |||
| .B \-d | |||
| is used, the record delimiter will be output before the matching | |||
| record. This option causes the delimiter to be output after the | |||
| matching record. | |||
| .PP | |||
| With no | |||
| .IR FILE , | |||
| or when | |||
| .I FILE | |||
| is -, reads standard input. If less than two | |||
| .IR FILE s | |||
| are given | |||
| .B \-h | |||
| is assumed, otherwise | |||
| .B \-H | |||
| is the default. | |||
| .SH DIAGNOSTICS | |||
| Exit status is 0 if a match is found, 1 for no match, and 2 if there | |||
| were errors. If | |||
| .B \-E | |||
| or -\fI#\fR is not specified, only exact matches are selected. | |||
| .PP | |||
| .I PATTERN | |||
| is a POSIX extended regular expression (ERE) with the TRE extensions. | |||
| .SH "REPORTING BUGS" | |||
| Report bugs to the TRE mailing list | |||
| .BR "" < tre-general@lists.laurikari.net >. | |||
| .SH COPYRIGHT | |||
| Copyright \(co 2002-2004 Ville Laurikari. | |||
| .br | |||
| This is free software, and comes with ABSOLUTELY NO WARRANTY. | |||
| You are welcome to redistribute this software under certain | |||
| conditions; see the source for the full license text. | |||
| @@ -0,0 +1,35 @@ | |||
| a:link { | |||
| color: #454892; | |||
| } | |||
| a:visited { | |||
| color: #665556; | |||
| } | |||
| p { | |||
| text-align: justify; | |||
| } | |||
| font.type { | |||
| color: #107020; | |||
| } | |||
| font.func { | |||
| color: #1010a0; | |||
| } | |||
| font.arg { | |||
| color: #906000; | |||
| } | |||
| font.qual { | |||
| color: #501050; | |||
| } | |||
| tr.title { | |||
| background: #cbc5b8; | |||
| } | |||
| tr.even { | |||
| background: #dbdbdb; | |||
| } | |||
| tr.odd { | |||
| background: #ebebee; | |||
| } | |||
| div.code { | |||
| background: #e0e0f0; | |||
| padding: 10px; | |||
| } | |||
| @@ -0,0 +1,821 @@ | |||
| <h1>TRE API reference manual</h1> | |||
| <h2>The <tt>regcomp()</tt> functions</h2> | |||
| <a name="regcomp"></a> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="type">int</font> | |||
| <font class="func">regcomp</font>(<font | |||
| class="type">regex_t</font> *<font class="arg">preg</font>, | |||
| <font class="qual">const</font> <font class="type">char</font> | |||
| *<font class="arg">regex</font>, <font class="type">int</font> | |||
| <font class="arg">cflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regncomp</font>(<font class="type">regex_t</font> | |||
| *<font class="arg">preg</font>, <font class="qual">const</font> | |||
| <font class="type">char</font> *<font class="arg">regex</font>, | |||
| <font class="type">size_t</font> <font class="arg">len</font>, | |||
| <font class="type">int</font> <font class="arg">cflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regwcomp</font>(<font class="type">regex_t</font> | |||
| *<font class="arg">preg</font>, <font class="qual">const</font> | |||
| <font class="type">wchar_t</font> *<font | |||
| class="arg">regex</font>, <font class="type">int</font> <font | |||
| class="arg">cflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regwncomp</font>(<font class="type">regex_t</font> | |||
| *<font class="arg">preg</font>, <font class="qual">const</font> | |||
| <font class="type">wchar_t</font> *<font | |||
| class="arg">regex</font>, <font class="type">size_t</font> | |||
| <font class="arg">len</font>, <font class="type">int</font> | |||
| <font class="arg">cflags</font>); | |||
| <br> | |||
| <font class="type">void</font> <font | |||
| class="func">regfree</font>(<font class="type">regex_t</font> | |||
| *<font class="arg">preg</font>); | |||
| <br> | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">regcomp</font>()</tt> function compiles | |||
| the regex string pointed to by <tt><font | |||
| class="arg">regex</font></tt> to an internal representation and | |||
| stores the result in the pattern buffer structure pointed to by | |||
| <tt><font class="arg">preg</font></tt>. The <tt><font | |||
| class="func">regncomp</font>()</tt> function is like <tt><font | |||
| class="func">regcomp</font>()</tt>, but <tt><font | |||
| class="arg">regex</font></tt> is not terminated with the null | |||
| byte. Instead, the <tt><font class="arg">len</font></tt> argument | |||
| is used to give the length of the string, and the string may contain | |||
| null bytes. The <tt><font class="func">regwcomp</font>()</tt> and | |||
| <tt><font class="func">regwncomp</font>()</tt> functions work like | |||
| <tt><font class="func">regcomp</font>()</tt> and <tt><font | |||
| class="func">regncomp</font>()</tt>, respectively, but take a wide | |||
| character (<tt><font class="type">wchar_t</font></tt>) string | |||
| instead of a byte string. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="arg">cflags</font></tt> argument is a the | |||
| bitwise inclusive OR of zero or more of the following flags (defined | |||
| in the header <tt><tre/regex.h></tt>): | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>REG_EXTENDED</tt></dt> | |||
| <dd>Use POSIX Extended Regular Expression (ERE) compatible syntax when | |||
| compiling <tt><font class="arg">regex</font></tt>. The default | |||
| syntax is the POSIX Basic Regular Expression (BRE) syntax, but it is | |||
| considered obsolete.</dd> | |||
| <dt><tt>REG_ICASE</tt></dt> | |||
| <dd>Ignore case. Subsequent searches with the <a | |||
| href="#regexec"><tt>regexec</tt></a> family of functions using this | |||
| pattern buffer will be case insensitive.</dd> | |||
| <dt><tt>REG_NOSUB</tt></dt> | |||
| <dd>Do not report submatches. Subsequent searches with the <a | |||
| href="#regexec"><tt>regexec</tt></a> family of functions will only | |||
| report whether a match was found or not and will not fill the submatch | |||
| array.</dd> | |||
| <dt><tt>REG_NEWLINE</tt></dt> | |||
| <dd>Normally the newline character is treated as an ordinary | |||
| character. When this flag is used, the newline character | |||
| (<tt>'\n'</tt>, ASCII code 10) is treated specially as follows: | |||
| <ol> | |||
| <li>The match-any-character operator (dot <tt>"."</tt> outside a | |||
| bracket expression) does not match a newline.</li> | |||
| <li>A non-matching list (<tt>[^...]</tt>) not containing a newline | |||
| does not match a newline.</li> | |||
| <li>The match-beginning-of-line operator <tt>^</tt> matches the empty | |||
| string immediately after a newline as well as the empty string at the | |||
| beginning of the string (but see the <code>REG_NOTBOL</code> | |||
| <code>regexec()</code> flag below). | |||
| <li>The match-end-of-line operator <tt>$</tt> matches the empty | |||
| string immediately before a newline as well as the empty string at the | |||
| end of the string (but see the <code>REG_NOTEOL</code> | |||
| <code>regexec()</code> flag below). | |||
| </ol> | |||
| </dd> | |||
| <dt><tt>REG_LITERAL</tt></dt> | |||
| <dd>Interpret the entire <tt><font class="arg">regex</font></tt> | |||
| argument as a literal string, that is, all characters will be | |||
| considered ordinary. This is a nonstandard extension, compatible with | |||
| but not specified by POSIX.</dd> | |||
| <dt><tt>REG_NOSPEC</tt></dt> | |||
| <dd>Same as <tt>REG_LITERAL</tt>. This flag is provided for | |||
| compatibility with BSD.</dd> | |||
| <dt><tt>REG_RIGHT_ASSOC</tt></dt> | |||
| <dd>By default, concatenation is left associative in TRE, as per | |||
| the grammar given in the <a | |||
| href="http://www.opengroup.org/onlinepubs/007904975/basedefs/xbd_chap09.html">base | |||
| specifications on regular expressions</a> of Std 1003.1-2001 (POSIX). | |||
| This flag flips associativity of concatenation to right associative. | |||
| Associativity can have an effect on how a match is divided into | |||
| submatches, but does not change what is matched by the entire regexp. | |||
| </dd> | |||
| <dt><tt>REG_UNGREEDY</tt></dt> | |||
| <dd>By default, repetition operators are greedy in TRE as per Std 1003.1-2001 (POSIX) and | |||
| can be forced to be non-greedy by appending a <tt>?</tt> character. This flag reverses this behavior | |||
| by making the operators non-greedy by default and greedy when a <tt>?</tt> is specified.</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| After a successful call to <tt><font class="func">regcomp</font></tt> it is | |||
| possible to use the <tt><font class="arg">preg</font></tt> pattern buffer for | |||
| searching for matches in strings (see below). Once the pattern buffer is no | |||
| longer needed, it should be freed with <tt><font | |||
| class="func">regfree</font></tt> to free the memory allocated for it. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="type">regex_t</font></tt> structure has the | |||
| following fields that the application can read: | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt><font class="type">size_t</font> <font | |||
| class="arg">re_nsub</font></tt></dt> | |||
| <dd>Number of parenthesized subexpressions in <tt><font | |||
| class="arg">regex</font></tt>. | |||
| </dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| The <tt><font class="func">regcomp</font></tt> function returns | |||
| zero if the compilation was successful, or one of the following error | |||
| codes if there was an error: | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>REG_BADPAT</tt></dt> | |||
| <dd>Invalid regexp. TRE returns this only if a multibyte character | |||
| set is used in the current locale, and <tt><font | |||
| class="arg">regex</font></tt> contained an invalid multibyte | |||
| sequence.</dd> | |||
| <dt><tt>REG_ECOLLATE</tt></dt> | |||
| <dd>Invalid collating element referenced. TRE returns this whenever | |||
| equivalence classes or multicharacter collating elements are used in | |||
| bracket expressions (they are not supported yet).</dd> | |||
| <dt><tt>REG_ECTYPE</tt></dt> | |||
| <dd>Unknown character class name in <tt>[[:<i>name</i>:]]</tt>.</dd> | |||
| <dt><tt>REG_EESCAPE</tt></dt> | |||
| <dd>The last character of <tt><font class="arg">regex</font></tt> | |||
| was a backslash (<tt>\</tt>).</dd> | |||
| <dt><tt>REG_ESUBREG</tt></dt> | |||
| <dd>Invalid back reference; number in <tt>\<i>digit</i></tt> | |||
| invalid.</dd> | |||
| <dt><tt>REG_EBRACK</tt></dt> | |||
| <dd><tt>[]</tt> imbalance.</dd> | |||
| <dt><tt>REG_EPAREN</tt></dt> | |||
| <dd><tt>\(\)</tt> or <tt>()</tt> imbalance.</dd> | |||
| <dt><tt>REG_EBRACE</tt></dt> | |||
| <dd><tt>\{\}</tt> or <tt>{}</tt> imbalance.</dd> | |||
| <dt><tt>REG_BADBR</tt></dt> | |||
| <dd><tt>{}</tt> content invalid: not a number, more than two numbers, | |||
| first larger than second, or number too large. | |||
| <dt><tt>REG_ERANGE</tt></dt> | |||
| <dd>Invalid character range, e.g. ending point is earlier in the | |||
| collating order than the starting point.</dd> | |||
| <dt><tt>REG_ESPACE</tt></dt> | |||
| <dd>Out of memory, or an internal limit exceeded.</dd> | |||
| <dt><tt>REG_BADRPT</tt></dt> | |||
| <dd>Invalid use of repetition operators: two or more repetition operators have | |||
| been chained in an undefined way.</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <h2>The <tt>regexec()</tt> functions</h2> | |||
| <a name="regexec"></a> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">char</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font | |||
| class="arg">nmatch</font>, | |||
| <br> | |||
| <font class="type">regmatch_t</font> <font | |||
| class="arg">pmatch</font>[], <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regnexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">char</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font class="arg">len</font>, | |||
| <br> | |||
| <font class="type">size_t</font> <font | |||
| class="arg">nmatch</font>, <font class="type">regmatch_t</font> | |||
| <font class="arg">pmatch</font>[], <font | |||
| class="type">int</font> <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regwexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">wchar_t</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font | |||
| class="arg">nmatch</font>, | |||
| <br> | |||
| <font class="type">regmatch_t</font> <font | |||
| class="arg">pmatch</font>[], <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regwnexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">wchar_t</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font class="arg">len</font>, | |||
| <br> | |||
| | |||
| <font class="type">size_t</font> <font | |||
| class="arg">nmatch</font>, <font class="type">regmatch_t</font> | |||
| <font class="arg">pmatch</font>[], <font | |||
| class="type">int</font> <font class="arg">eflags</font>); | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">regexec</font>()</tt> function matches | |||
| the null-terminated string against the compiled regexp <tt><font | |||
| class="arg">preg</font></tt>, initialized by a previous call to | |||
| any one of the <a href="#regcomp"><tt>regcomp</tt></a> functions. The | |||
| <tt><font class="func">regnexec</font>()</tt> function is like | |||
| <tt><font class="func">regexec</font>()</tt>, but <tt><font | |||
| class="arg">string</font></tt> is not terminated with a null byte. | |||
| Instead, the <tt><font class="arg">len</font></tt> argument is used | |||
| to give the length of the string, and the string may contain null | |||
| bytes. The <tt><font class="func">regwexec</font>()</tt> and | |||
| <tt><font class="func">regwnexec</font>()</tt> functions work like | |||
| <tt><font class="func">regexec</font>()</tt> and <tt><font | |||
| class="func">regnexec</font>()</tt>, respectively, but take a wide | |||
| character (<tt><font class="type">wchar_t</font></tt>) string | |||
| instead of a byte string. The <tt><font | |||
| class="arg">eflags</font></tt> argument is a bitwise OR of zero or | |||
| more of the following flags: | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><code>REG_NOTBOL</code></dt> | |||
| <dd> | |||
| <p> | |||
| When this flag is used, the match-beginning-of-line operator | |||
| <tt>^</tt> does not match the empty string at the beginning of | |||
| <tt><font class="arg">string</font></tt>. If | |||
| <code>REG_NEWLINE</code> was used when compiling | |||
| <tt><font class="arg">preg</font></tt> the empty string | |||
| immediately after a newline character will still be matched. | |||
| </p> | |||
| </dd> | |||
| <dt><code>REG_NOTEOL</code></dt> | |||
| <dd> | |||
| <p> | |||
| When this flag is used, the match-end-of-line operator | |||
| <tt>$</tt> does not match the empty string at the end of | |||
| <tt><font class="arg">string</font></tt>. If | |||
| <code>REG_NEWLINE</code> was used when compiling | |||
| <tt><font class="arg">preg</font></tt> the empty string | |||
| immediately before a newline character will still be matched. | |||
| </p> | |||
| </dl> | |||
| <p> | |||
| These flags are useful when different portions of a string are passed | |||
| to <code>regexec</code> and the beginning or end of the partial string | |||
| should not be interpreted as the beginning or end of a line. | |||
| </p> | |||
| </blockquote> | |||
| <p> | |||
| If <code>REG_NOSUB</code> was used when compiling <tt><font | |||
| class="arg">preg</font></tt>, <tt><font | |||
| class="arg">nmatch</font></tt> is zero, or <tt><font | |||
| class="arg">pmatch</font></tt> is <code>NULL</code>, then the | |||
| <tt><font class="arg">pmatch</font></tt> argument is ignored. | |||
| Otherwise, the submatches corresponding to the parenthesized | |||
| subexpressions are filled in the elements of <tt><font | |||
| class="arg">pmatch</font></tt>, which must be dimensioned to have | |||
| at least <tt><font class="arg">nmatch</font></tt> elements. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="type">regmatch_t</font></tt> structure contains | |||
| at least the following fields: | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt><font class="type">regoff_t</font> <font | |||
| class="arg">rm_so</font></tt></dt> | |||
| <dd>Offset from start of <tt><font class="arg">string</font></tt> to start of | |||
| substring. </dd> | |||
| <dt><tt><font class="type">regoff_t</font> <font | |||
| class="arg">rm_eo</font></tt></dt> | |||
| <dd>Offset from start of <tt><font class="arg">string</font></tt> to the first | |||
| character after the substring. </dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| The length of a submatch can be computed by subtracting <code>rm_eo</code> and | |||
| <code>rm_so</code>. If a parenthesized subexpression did not participate in a | |||
| match, the <code>rm_so</code> and <code>rm_eo</code> fields for the | |||
| corresponding <code>pmatch</code> element are set to <code>-1</code>. Note | |||
| that when a multibyte character set is in effect, the submatch offsets are | |||
| given as byte offsets, not character offsets. | |||
| </p> | |||
| <p> | |||
| The <code>regexec()</code> functions return zero if a match was found, | |||
| otherwise they return <code>REG_NOMATCH</code> to indicate no match, | |||
| or <code>REG_ESPACE</code> to indicate that enough temporary memory | |||
| could not be allocated to complete the matching operation. | |||
| </p> | |||
| <h3>reguexec()</h3> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="qual">typedef struct</font> { | |||
| <br> | |||
| <font class="type">int</font> (*get_next_char)(<font | |||
| class="type">tre_char_t</font> *<font class="arg">c</font>, <font | |||
| class="type">unsigned int</font> *<font class="arg">pos_add</font>, | |||
| <font class="type">void</font> *<font class="arg">context</font>); | |||
| <br> | |||
| <font class="type">void</font> (*rewind)(<font | |||
| class="type">size_t</font> <font class="arg">pos</font>, <font | |||
| class="type">void</font> *<font class="arg">context</font>); | |||
| <br> | |||
| <font class="type">int</font> (*compare)(<font | |||
| class="type">size_t</font> <font class="arg">pos1</font>, <font | |||
| class="type">size_t</font> <font class="arg">pos2</font>, <font | |||
| class="type">size_t</font> <font class="arg">len</font>, <font | |||
| class="type">void</font> *<font class="arg">context</font>); | |||
| <br> | |||
| <font class="type">void</font> *<font | |||
| class="arg">context</font>; | |||
| <br> | |||
| } <font class="type">tre_str_source</font>; | |||
| <br> | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">reguexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">tre_str_source</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font class="arg">nmatch</font>, | |||
| <br> | |||
| <font class="type">regmatch_t</font> <font | |||
| class="arg">pmatch</font>[], <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">reguexec</font>()</tt> function works just | |||
| like the other <tt>regexec()</tt> functions, except that the input | |||
| string is read from user specified callback functions instead of a | |||
| character array. This makes it possible, for example, to match | |||
| regexps over arbitrary user specified data structures. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="type">tre_str_source</font></tt> structure | |||
| contains the following fields: | |||
| </p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>get_next_char</tt></dt> | |||
| <dd>This function must retrieve the next available character. If a | |||
| character is not available, the space pointed to by | |||
| <tt><font class="arg">c</font></tt> must be set to zero and it must return | |||
| a nonzero value. If a character is available, it must be stored | |||
| to the space pointed to by | |||
| <tt><font class="arg">c</font></tt>, and the integer pointer to by | |||
| <tt><font class="arg">pos_add</font></tt> must be set to the | |||
| number of units advanced in the input (the value must be | |||
| <tt>>=1</tt>), and zero must be returned.</dd> | |||
| <dt><tt>rewind</tt></dt> | |||
| <dd>This function must rewind the input stream to the position | |||
| specified by <tt><font class="arg">pos</font></tt>. Unless the regexp | |||
| uses back references, <tt>rewind</tt> is not needed and can be set to | |||
| <tt>NULL</tt>.</dd> | |||
| <dt><tt>compare</tt></dt> | |||
| <dd>This function compares two substrings in the input streams | |||
| starting at the positions specified by <tt><font | |||
| class="arg">pos1</font></tt> and <tt><font | |||
| class="arg">pos2</font></tt> of length <tt><font | |||
| class="arg">len</font></tt>. If the substrings are equal, | |||
| <tt>compare</tt> must return zero, otherwise a nonzero value must be | |||
| returned. Unless the regexp uses back references, <tt>compare</tt> is | |||
| not needed and can be set to <tt>NULL</tt>.</dd> | |||
| <dt><tt>context</tt></dt> | |||
| <dd>This is a context variable, passed as the last argument to | |||
| all of the above functions for keeping track of the internal state of | |||
| the users code.</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| The position in the input stream is measured in <tt><font | |||
| class="type">size_t</font></tt> units. The current position is the | |||
| sum of the increments gotten from <tt><font | |||
| class="arg">pos_add</font></tt> (plus the position of the last | |||
| <tt>rewind</tt>, if any). The starting position is zero. Submatch | |||
| positions filled in the <tt><font class="arg">pmatch</font>[]</tt> | |||
| array are, of course, given using positions computed in this way. | |||
| </p> | |||
| <p> | |||
| For an example of how to use <tt>reguexec()</tt>, see the | |||
| <tt>tests/test-str-source.c</tt> file in the TRE source code | |||
| distribution. | |||
| </p> | |||
| <h2>The approximate matching functions</h2> | |||
| <a name="regaexec"></a> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="qual">typedef struct</font> {<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">cost_ins</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">cost_del</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">cost_subst</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">max_cost</font>;<br><br> | |||
| <font class="type">int</font> | |||
| <font class="arg">max_ins</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">max_del</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">max_subst</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">max_err</font>;<br> | |||
| } <font class="type">regaparams_t</font>;<br> | |||
| <br> | |||
| <font class="qual">typedef struct</font> {<br> | |||
| <font class="type">size_t</font> | |||
| <font class="arg">nmatch</font>;<br> | |||
| <font class="type">regmatch_t</font> | |||
| *<font class="arg">pmatch</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">cost</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">num_ins</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">num_del</font>;<br> | |||
| <font class="type">int</font> | |||
| <font class="arg">num_subst</font>;<br> | |||
| } <font class="type">regamatch_t</font>;<br> | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regaexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">char</font> *<font class="arg">string</font>,<br> | |||
| | |||
| <font class="type">regamatch_t</font> | |||
| *<font class="arg">match</font>, | |||
| <font class="type">regaparams_t</font> | |||
| <font class="arg">params</font>, | |||
| <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">reganexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">char</font> *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> <font class="arg">len</font>,<br> | |||
| | |||
| <font class="type">regamatch_t</font> | |||
| *<font class="arg">match</font>, | |||
| <font class="type">regaparams_t</font> | |||
| <font class="arg">params</font>, | |||
| <font class="type">int</font> <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">regawexec</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font | |||
| class="arg">preg</font>, <font class="qual">const</font> <font | |||
| class="type">wchar_t</font> *<font class="arg">string</font>,<br> | |||
| | |||
| <font class="type">regamatch_t</font> | |||
| *<font class="arg">match</font>, | |||
| <font class="type">regaparams_t</font> | |||
| <font class="arg">params</font>, | |||
| <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| <br> | |||
| <font class="type">int</font> | |||
| <font class="func">regawnexec</font>( | |||
| <font class="qual">const</font> | |||
| <font class="type">regex_t</font> | |||
| *<font class="arg">preg</font>, | |||
| <font class="qual">const</font> | |||
| <font class="type">wchar_t</font> | |||
| *<font class="arg">string</font>, | |||
| <font class="type">size_t</font> | |||
| <font class="arg">len</font>,<br> | |||
| | |||
| <font class="type">regamatch_t</font> | |||
| *<font class="arg">match</font>, | |||
| <font class="type">regaparams_t</font> | |||
| <font class="arg">params</font>, | |||
| <font class="type">int</font> | |||
| <font class="arg">eflags</font>); | |||
| <br> | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">regaexec</font>()</tt> function searches for | |||
| the best match in <tt><font class="arg">string</font></tt> | |||
| against the compiled regexp <tt><font | |||
| class="arg">preg</font></tt>, initialized by a previous call to | |||
| any one of the <a href="#regcomp"><tt>regcomp</tt></a> functions. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="func">reganexec</font>()</tt> function is like | |||
| <tt><font class="func">regaexec</font>()</tt>, but <tt><font | |||
| class="arg">string</font></tt> is not terminated by a null byte. | |||
| Instead, the <tt><font class="arg">len</font></tt> argument is used to | |||
| tell the length of the string, and the string may contain null | |||
| bytes. The <tt><font class="func">regawexec</font>()</tt> and | |||
| <tt><font class="func">regawnexec</font>()</tt> functions work like | |||
| <tt><font class="func">regaexec</font>()</tt> and <tt><font | |||
| class="func">reganexec</font>()</tt>, respectively, but take a wide | |||
| character (<tt><font class="type">wchar_t</font></tt>) string instead | |||
| of a byte string. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="arg">eflags</font></tt> argument is like for | |||
| the regexec() functions. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="arg">params</font></tt> struct controls the | |||
| approximate matching parameters: | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">cost_ins</font></tt></dt> | |||
| <dd>The default cost of an inserted character, that is, an extra | |||
| character in <tt><font class="arg">string</font></tt>.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">cost_del</font></tt></dt> | |||
| <dd>The default cost of a deleted character, that is, a character | |||
| missing from <tt><font class="arg">string</font></tt>.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">cost_subst</font></tt></dt> | |||
| <dd>The default cost of a substituted character.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">max_cost</font></tt></dt> | |||
| <dd>The maximum allowed cost of a match. If this is set to zero, | |||
| an exact matching is searched for, and results equivalent to | |||
| those returned by the <tt>regexec()</tt> functions are | |||
| returned.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">max_ins</font></tt></dt> | |||
| <dd>Maximum allowed number of inserted characters.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">max_del</font></tt></dt> | |||
| <dd>Maximum allowed number of deleted characters.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">max_subst</font></tt></dt> | |||
| <dd>Maximum allowed number of substituted characters.</dd> | |||
| <dt><tt><font class="type">int</font></tt> | |||
| <tt><font class="arg">max_err</font></tt></dt> | |||
| <dd>Maximum allowed number of errors (inserts + deletes + | |||
| substitutes).</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| The <tt><font class="arg">match</font></tt> argument points to a | |||
| <tt><font class="type">regamatch_t</font></tt> structure. The | |||
| <tt><font class="arg">nmatch</font></tt> and <tt><font | |||
| class="arg">pmatch</font></tt> field must be filled by the caller. If | |||
| <code>REG_NOSUB</code> was used when compiling the regexp, or | |||
| <code>match->nmatch</code> is zero, or | |||
| <code>match->pmatch</code> is <code>NULL</code>, the | |||
| <code>match->pmatch</code> argument is ignored. Otherwise, the | |||
| submatches corresponding to the parenthesized subexpressions are | |||
| filled in the elements of <code>match->pmatch</code>, which must be | |||
| dimensioned to have at least <code>match->nmatch</code> elements. | |||
| The <code>match->cost</code> field is set to the cost of the match | |||
| found, and the <code>match->num_ins</code>, | |||
| <code>match->num_del</code>, and <code>match->num_subst</code> | |||
| fields are set to the number of inserts, deletes, and substitutes in | |||
| the match, respectively. | |||
| </p> | |||
| <p> | |||
| The <tt>regaexec()</tt> functions return zero if a match with cost | |||
| smaller than <code>params->max_cost</code> was found, otherwise | |||
| they return <code>REG_NOMATCH</code> to indicate no match, or | |||
| <code>REG_ESPACE</code> to indicate that enough temporary memory could | |||
| not be allocated to complete the matching operation. | |||
| </p> | |||
| <h2>Miscellaneous</h2> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">tre_have_backrefs</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font class="arg">preg</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">tre_have_approx</font>(<font class="qual">const</font> | |||
| <font class="type">regex_t</font> *<font class="arg">preg</font>); | |||
| <br> | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">tre_have_backrefs</font>()</tt> and | |||
| <tt><font class="func">tre_have_approx</font>()</tt> functions return | |||
| 1 if the compiled pattern has back references or uses approximate | |||
| matching, respectively, and 0 if not. | |||
| </p> | |||
| <h2>Checking build time options</h2> | |||
| <a name="tre_config"></a> | |||
| <div class="code"> | |||
| <code> | |||
| #include <tre/regex.h> | |||
| <br> | |||
| <br> | |||
| <font class="type">char</font> *<font | |||
| class="func">tre_version</font>(<font class="type">void</font>); | |||
| <br> | |||
| <font class="type">int</font> <font | |||
| class="func">tre_config</font>(<font class="type">int</font> <font | |||
| class="arg">query</font>, <font class="type">void</font> *<font | |||
| class="arg">result</font>); | |||
| <br> | |||
| </code> | |||
| </div> | |||
| <p> | |||
| The <tt><font class="func">tre_config</font>()</tt> function can be | |||
| used to retrieve information of which optional features have been | |||
| compiled into the TRE library and information of other parameters that | |||
| may change between releases. | |||
| </p> | |||
| <p> | |||
| The <tt><font class="arg">query</font></tt> argument is an integer | |||
| telling what information is requested for. The <tt><font | |||
| class="arg">result</font></tt> argument is a pointer to a variable | |||
| where the information is returned. The return value of a call to | |||
| <tt><font class="func">tre_config</font>()</tt> is zero if <tt><font | |||
| class="arg">query</font></tt> was recognized, REG_NOMATCH otherwise. | |||
| </p> | |||
| <p> | |||
| The following values are recognized for <tt><font | |||
| class="arg">query</font></tt>: | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>TRE_CONFIG_APPROX</tt></dt> | |||
| <dd>The result is an integer that is set to one if approximate | |||
| matching support is available, zero if not.</dd> | |||
| <dt><tt>TRE_CONFIG_WCHAR</tt></dt> | |||
| <dd>The result is an integer that is set to one if wide character | |||
| support is available, zero if not.</dd> | |||
| <dt><tt>TRE_CONFIG_MULTIBYTE</tt></dt> | |||
| <dd>The result is an integer that is set to one if multibyte character | |||
| set support is available, zero if not.</dd> | |||
| <dt><tt>TRE_CONFIG_SYSTEM_ABI</tt></dt> | |||
| <dd>The result is an integer that is set to one if TRE has been | |||
| compiled to be compatible with the system regex ABI, zero if not.</dd> | |||
| <dt><tt>TRE_CONFIG_VERSION</tt></dt> | |||
| <dd>The result is a pointer to a static character string that gives | |||
| the version of the TRE library.</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <p> | |||
| The <tt><font class="func">tre_version</font>()</tt> function returns | |||
| a short human readable character string which shows the software name, | |||
| version, and license. | |||
| <h2>Preprocessor definitions</h2> | |||
| <p>The header <tt><tre/regex.h></tt> defines certain | |||
| C preprocessor symbols. | |||
| <h3>Version information</h3> | |||
| <p>The following definitions may be useful for checking whether a new | |||
| enough version is being used. Note that it is recommended to use the | |||
| <tt>pkg-config</tt> tool for version and other checks in Autoconf | |||
| scripts.</p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>TRE_VERSION</tt></dt> | |||
| <dd>The version string. </dd> | |||
| <dt><tt>TRE_VERSION_1</tt></dt> | |||
| <dd>The major version number (first part of version string).</dd> | |||
| <dt><tt>TRE_VERSION_2</tt></dt> | |||
| <dd>The minor version number (second part of version string).</dd> | |||
| <dt><tt>TRE_VERSION_3</tt></dt> | |||
| <dd>The micro version number (third part of version string).</dd> | |||
| </dl> | |||
| </blockquote> | |||
| <h3>Features</h3> | |||
| <p>The following definitions may be useful for checking whether all | |||
| necessary features are enabled. Use these only if compile time | |||
| checking suffices (linking statically with TRE). When linking | |||
| dynamically <a href="#tre_config"><tt>tre_config()</tt></a> should be used | |||
| instead.</p> | |||
| <blockquote> | |||
| <dl> | |||
| <dt><tt>TRE_APPROX</tt></dt> | |||
| <dd>This is defined if approximate matching support is enabled. The | |||
| prototypes for approximate matching functions are defined only if | |||
| <tt>TRE_APPROX</tt> is defined.</dd> | |||
| <dt><tt>TRE_WCHAR</tt></dt> | |||
| <dd>This is defined if wide character support is enabled. The | |||
| prototypes for wide character matching functions are defined only if | |||
| <tt>TRE_WCHAR</tt> is defined.</dd> | |||
| <dt><tt>TRE_MULTIBYTE</tt></dt> | |||
| <dd>This is defined if multibyte character set support is enabled. | |||
| If this is not set any locale settings are ignored, and the default | |||
| locale is used when parsing regexps and matching strings.</dd> | |||
| </dl> | |||
| </blockquote> | |||
| @@ -0,0 +1,433 @@ | |||
| <h1>TRE Regexp Syntax</h1> | |||
| <p> | |||
| This document describes the POSIX 1003.2 extended RE (ERE) syntax and | |||
| the basic RE (BRE) syntax as implemented by TRE, and the TRE extensions | |||
| to the ERE syntax. A simple Extended Backus-Naur Form (EBNF) style | |||
| notation is used to describe the grammar. | |||
| </p> | |||
| <h2>ERE Syntax</h2> | |||
| <h3>Alternation operator</h3> | |||
| <a name="alternation"></a> | |||
| <a name="extended-regexp"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>extended-regexp</i> ::= <a href="#branch"><i>branch</i></a> | |||
| | <i>extended-regexp</i> <b>"|"</b> <a href="#branch"><i>branch</i></a> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| An extended regexp (ERE) is one or more <i>branches</i>, separated by | |||
| <tt>|</tt>. An ERE matches anything that matches one or more of the | |||
| branches. | |||
| </p> | |||
| <h3>Catenation of REs</h3> | |||
| <a name="catenation"></a> | |||
| <a name="branch"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>branch</i> ::= <i>piece</i> | |||
| | <i>branch</i> <i>piece</i> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| A branch is one or more <i>pieces</i> concatenated. It matches a | |||
| match for the first piece, followed by a match for the second piece, | |||
| and so on. | |||
| </p> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>piece</i> ::= <i>atom</i> | |||
| | <i>atom</i> <a href="#repeat-operator"><i>repeat-operator</i></a> | |||
| | <i>atom</i> <a href="#approx-settings"><i>approx-settings</i></a> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| A piece is an <i>atom</i> possibly followed by a repeat operator or an | |||
| expression controlling approximate matching parameters for the <i>atom</i>. | |||
| </p> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>atom</i> ::= <b>"("</b> <i>extended-regexp</i> <b>")"</b> | |||
| | <a href="#bracket-expression"><i>bracket-expression</i></a> | |||
| | <b>"."</b> | |||
| | <a href="#assertion"><i>assertion</i></a> | |||
| | <a href="#literal"><i>literal</i></a> | |||
| | <a href="#backref"><i>back-reference</i></a> | |||
| | <b>"(?#"</b> <i>comment-text</i> <b>")"</b> | |||
| | <b>"(?"</b> <a href="#options"><i>options</i></a> <b>")"</b> <i>extended-regexp</i> | |||
| | <b>"(?"</b> <a href="#options"><i>options</i></a> <b>":"</b> <i>extended-regexp</i> <b>")"</b> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| An atom is either an ERE enclosed in parenthesis, a bracket | |||
| expression, a <tt>.</tt> (period), an assertion, or a literal. | |||
| </p> | |||
| <p> | |||
| The dot (<tt>.</tt>) matches any single character. | |||
| If the <code>REG_NEWLINE</code> compilation flag (see <a | |||
| href="api.html">API manual</a>) is specified, the newline | |||
| character is not matched. | |||
| </p> | |||
| <p> | |||
| <tt>Comment-text</tt> can contain any characters except for a closing parenthesis <tt>)</tt>. The text in the comment is | |||
| completely ignored by the regex parser and it used solely for readability purposes. | |||
| </p> | |||
| <h3>Repeat operators</h3> | |||
| <a name="repeat-operator"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>repeat-operator</i> ::= <b>"*"</b> | |||
| | <b>"+"</b> | |||
| | <b>"?"</b> | |||
| | <i>bound</i> | |||
| | <b>"*?"</b> | |||
| | <b>"+?"</b> | |||
| | <b>"??"</b> | |||
| | <i>bound</i> <b>?</b> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| An atom followed by <tt>*</tt> matches a sequence of 0 or more matches | |||
| of the atom. <tt>+</tt> is similar to <tt>*</tt>, matching a sequence | |||
| of 1 or more matches of the atom. An atom followed by <tt>?</tt> | |||
| matches a sequence of 0 or 1 matches of the atom. | |||
| </p> | |||
| <p> | |||
| A <i>bound</i> is one of the following, where <i>m</i> and <i>m</i> | |||
| are unsigned decimal integers between <tt>0</tt> and | |||
| <tt>RE_DUP_MAX</tt>: | |||
| </p> | |||
| <ol> | |||
| <li><tt>{</tt><i>m</i><tt>,</tt><i>n</i><tt>}</tt></li> | |||
| <li><tt>{</tt><i>m</i><tt>,}</tt></li> | |||
| <li><tt>{</tt><i>m</i><tt>}</tt></li> | |||
| </ol> | |||
| <p> | |||
| An atom followed by [1] matches a sequence of <i>m</i> through <i>n</i> | |||
| (inclusive) matches of the atom. An atom followed by [2] | |||
| matches a sequence of <i>m</i> or more matches of the atom. An atom | |||
| followed by [3] matches a sequence of exactly <i>m</i> matches of the | |||
| atom. | |||
| </p> | |||
| <p> | |||
| Adding a <tt>?</tt> to a repeat operator makes the subexpression minimal, or | |||
| non-greedy. Normally a repeated expression is greedy, that is, it matches as | |||
| many characters as possible. A non-greedy subexpression matches as few | |||
| characters as possible. Note that this does not (always) mean the same thing | |||
| as matching as many or few repetitions as possible. Also note | |||
| that <strong>minimal repetitions are not currently supported for approximate | |||
| matching</strong>. | |||
| </p> | |||
| <h3>Approximate matching settings</h3> | |||
| <a name="approx-settings"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>approx-settings</i> ::= <b>"{"</b> <i>count-limits</i>* <b>","</b>? <i>cost-equation</i>? <b>"}"</b> | |||
| <i>count-limits</i> ::= <b>"+"</b> <i>number</i>? | |||
| | <b>"-"</b> <i>number</i>? | |||
| | <b>"#"</b> <i>number</i>? | |||
| | <b>"~"</b> <i>number</i>? | |||
| <i>cost-equation</i> ::= ( <i>cost-term</i> "+"? " "? )+ <b>"<"</b> <i>number</i> | |||
| <i>cost-term</i> ::= <i>number</i> <b>"i"</b> | |||
| | <i>number</i> <b>"d"</b> | |||
| | <i>number</i> <b>"s"</b> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| The approximate matching settings for a subpattern can be changed | |||
| by appending <i>approx-settings</i> to the subpattern. Limits for | |||
| the number of errors can be set and an expression for specifying and | |||
| limiting the costs can be given. | |||
| </p> | |||
| <p> | |||
| The <i>count-limits</i> can be used to set limits for the number of | |||
| insertions (<tt>+</tt>), deletions (<tt>-</tt>), substitutions | |||
| (<tt>#</tt>), and total number of errors (<tt>~</tt>). If the | |||
| <i>number</i> part is omitted, the specified error count will be | |||
| unlimited. | |||
| </p> | |||
| <p> | |||
| The <i>cost-equation</i> can be thought of as a mathematical equation, | |||
| where <tt>i</tt>, <tt>d</tt>, and <tt>s</tt> stand for the number of | |||
| insertions, deletions, and substitutions, respectively. The equation | |||
| can have a multiplier for each of <tt>i</tt>, <tt>d</tt>, and | |||
| <tt>s</tt>. The multiplier is the cost of the error, and the number | |||
| after <tt><</tt> is the maximum allowed cost of a match. Spaces | |||
| and pluses can be inserted to make the equation readable. In fact, when | |||
| specifying only a cost equation, adding a space after the opening <tt>{</tt> | |||
| is <strong>required</strong>. | |||
| </p> | |||
| <p> | |||
| Examples: | |||
| <dl> | |||
| <dt><tt>{~}</tt></dt> | |||
| <dd>Sets the maximum number of errors to unlimited.</dd> | |||
| <dt><tt>{~3}</tt></dt> | |||
| <dd>Sets the maximum number of errors to three.</dd> | |||
| <dt><tt>{+2~5}</tt></dt> | |||
| <dd>Sets the maximum number of errors to five, and the maximum number | |||
| of insertions to two.</dd> | |||
| <dt><tt>{<3}</tt></dt> | |||
| <dd>Sets the maximum cost to three. | |||
| <dt><tt>{ 2i + 1d + 2s < 5 }</tt></dt> | |||
| <dd>Sets the cost of an insertion to two, a deletion to one, a | |||
| substitution to two, and the maximum cost to five. | |||
| </dl> | |||
| <h3>Bracket expressions</h3> | |||
| <a name="bracket-expression"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>bracket-expression</i> ::= <b>"["</b> <i>item</i>+ <b>"]"</b> | |||
| | <b>"[^"</b> <i>item</i>+ <b>"]"</b> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| A bracket expression specifies a set of characters by enclosing a | |||
| nonempty list of items in brackets. Normally anything matching any | |||
| item in the list is matched. If the list begins with <tt>^</tt> the | |||
| meaning is negated; any character matching no item in the list is | |||
| matched. | |||
| </p> | |||
| <p> | |||
| An item is any of the following: | |||
| </p> | |||
| <ul> | |||
| <li>A single character, matching that character.</li> | |||
| <li>Two characters separated by <tt>-</tt>. This is shorthand for the | |||
| full range of characters between those two (inclusive) in the | |||
| collating sequence. For example, <tt>[0-9]</tt> in ASCII matches any | |||
| decimal digit.</li> | |||
| <li>A collating element enclosed in <tt>[.</tt> and <tt>.]</tt>, | |||
| matching the collating element. This can be used to include a literal | |||
| <tt>-</tt> or a multi-character collating element in the list.</li> | |||
| <li>A collating element enclosed in <tt>[=</tt> and <tt>=]</tt> (an | |||
| equivalence class), matching all collating elements with the same | |||
| primary collation weight as that element, including the element | |||
| itself.</li> | |||
| <li>The name of a character class enclosed in <tt>[:</tt> and | |||
| <tt>:]</tt>, matching any character belonging to the class. The set | |||
| of valid names depends on the <code>LC_CTYPE</code> category of the | |||
| current locale, but the following names are valid in all locales: | |||
| <ul> | |||
| <li><tt>alnum</tt> - alphanumeric characters</li> | |||
| <li><tt>alpha</tt> - alphabetic characters</li> | |||
| <li><tt>blank</tt> - blank characters</li> | |||
| <li><tt>cntrl</tt> - control characters</li> | |||
| <li><tt>digit</tt> - decimal digits (0 through 9)</li> | |||
| <li><tt>graph</tt> - all printable characters except space</li> | |||
| <li><tt>lower</tt> - lower-case letters</li> | |||
| <li><tt>print</tt> - printable characters including space</li> | |||
| <li><tt>punct</tt> - printable characters not space or alphanumeric</li> | |||
| <li><tt>space</tt> - white-space characters</li> | |||
| <li><tt>upper</tt> - upper case letters</li> | |||
| <li><tt>xdigit</tt> - hexadecimal digits</li> | |||
| </ul> | |||
| </ul> | |||
| <p> | |||
| To include a literal <tt>-</tt> in the list, make it either the first | |||
| or last item, the second endpoint of a range, or enclose it in | |||
| <tt>[.</tt> and <tt>.]</tt> to make it a collating element. To | |||
| include a literal <tt>]</tt> in the list, make it either the first | |||
| item, the second endpoint of a range, or enclose it in <tt>[.</tt> and | |||
| <tt>.]</tt>. To use a literal <tt>-</tt> as the first | |||
| endpoint of a range, enclose it in <tt>[.</tt> and <tt>.]</tt>. | |||
| </p> | |||
| <h3>Assertions</h3> | |||
| <a name="assertion"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>assertion</i> ::= <b>"^"</b> | |||
| | <b>"$"</b> | |||
| | <b>"\"</b> <i>assertion-character</i> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| The expressions <tt>^</tt> and <tt>$</tt> are called "left anchor" and | |||
| "right anchor", respectively. The left anchor matches the empty | |||
| string at the beginning of the string. The right anchor matches the | |||
| empty string at the end of the string. The behaviour of both anchors | |||
| can be varied by specifying certain execution and compilation flags; | |||
| see the <a href="api.html">API manual</a>. | |||
| </p> | |||
| <p> | |||
| An assertion-character can be any of the following: | |||
| </p> | |||
| <ul> | |||
| <li><tt><</tt> - Beginning of word | |||
| <li><tt>></tt> - End of word | |||
| <li><tt>b</tt> - Word boundary | |||
| <li><tt>B</tt> - Non-word boundary | |||
| <li><tt>d</tt> - Digit character (equivalent to <tt>[[:digit:]]</tt>)</li> | |||
| <li><tt>D</tt> - Non-digit character (equivalent to <tt>[^[:digit:]]</tt>)</li> | |||
| <li><tt>s</tt> - Space character (equivalent to <tt>[[:space:]]</tt>)</li> | |||
| <li><tt>S</tt> - Non-space character (equivalent to <tt>[^[:space:]]</tt>)</li> | |||
| <li><tt>w</tt> - Word character (equivalent to <tt>[[:alnum:]_]</tt>)</li> | |||
| <li><tt>W</tt> - Non-word character (equivalent to <tt>[^[:alnum:]_]</tt>)</li> | |||
| </ul> | |||
| <h3>Literals</h3> | |||
| <a name="literal"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>literal</i> ::= <i>ordinary-character</i> | |||
| | <b>"\x"</b> [<b>"1"</b>-<b>"9"</b> <b>"a"-<b>"f"</b> <b>"A"</b>-<b>"F"</b>]{0,2} | |||
| | <b>"\x{"</b> [<b>"1"</b>-<b>"9"</b> <b>"a"-<b>"f"</b> <b>"A"</b>-<b>"F"</b>]* <b>"}"</b> | |||
| | <b>"\"</b> <i>character</i> | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| A literal is either an ordinary character (a character that has no | |||
| other significance in the context), an 8 bit hexadecimal encoded | |||
| character (e.g. <tt>\x1B</tt>), a wide hexadecimal encoded character | |||
| (e.g. <tt>\x{263a}</tt>), or an escaped character. An escaped | |||
| character is a <tt>\</tt> followed by any character, and matches that | |||
| character. Escaping can be used to match characters which have a | |||
| special meaning in regexp syntax. A <tt>\</tt> cannot be the last | |||
| character of an ERE. Escaping also allows you to include a few | |||
| non-printable characters in the regular expression. These special | |||
| escape sequences include: | |||
| </p> | |||
| <ul> | |||
| <li><tt>\a</tt> - Bell character (ASCII code 7) | |||
| <li><tt>\e</tt> - Escape character (ASCII code 27) | |||
| <li><tt>\f</tt> - Form-feed character (ASCII code 12) | |||
| <li><tt>\n</tt> - New-line/line-feed character (ASCII code 10) | |||
| <li><tt>\r</tt> - Carriage return character (ASCII code 13) | |||
| <li><tt>\t</tt> - Horizontal tab character (ASCII code 9) | |||
| </ul> | |||
| <p> | |||
| An ordinary character is just a single character with no other | |||
| significance, and matches that character. A <tt>{</tt> followed by | |||
| something else than a digit is considered an ordinary character. | |||
| </p> | |||
| <h3>Back references</h3> | |||
| <a name="backref"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>back-reference</i> ::= <b>"\"</b> [<b>"1"</b>-<b>"9"</b>] | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| <p> | |||
| A back reference is a backslash followed by a single non-zero decimal | |||
| digit <i>d</i>. It matches the same sequence of characters | |||
| matched by the <i>d</i>th parenthesized subexpression. | |||
| </p> | |||
| <p> | |||
| Back references are not defined for POSIX EREs (for BREs they are), | |||
| but many matchers, including TRE, implement back references for both | |||
| EREs and BREs. | |||
| </p> | |||
| <h3>Options</h3> | |||
| <a name="options"></a> | |||
| <table bgcolor="#e0e0f0" cellpadding="10"> | |||
| <tr><td> | |||
| <pre> | |||
| <i>options</i> ::= [<b>"i" "n" "r" "U"</b>]* (<b>"-"</b> [<b>"i" "n" "r" "U"</b>]*)? | |||
| </pre> | |||
| </td></tr> | |||
| </table> | |||
| Options allow compile time options to be turned on/off for particular parts of the | |||
| regular expression. The options equate to several compile time options specified to | |||
| the regcomp API function. If the option is specified in the first section, it is | |||
| turned on. If it is specified in the second section (after the <tt>-</tt>), it is | |||
| turned off. | |||
| <ul> | |||
| <li>i - Case insensitive. | |||
| <li>n - Forces special handling of the new line character. See the REG_NEWLINE flag in | |||
| the <a href="tre-api.html">API Manual</a>. | |||
| <li>r - Causes the regex to be matched in a right associative manner rather than the normal | |||
| left associative manner. | |||
| <li>U - Forces repetition operators to be non-greedy unless a <tt>?</tt> is appended. | |||
| </ul> | |||
| <h2>BRE Syntax</h2> | |||
| <p> | |||
| The obsolete basic regexp (BRE) syntax differs from the ERE syntax as | |||
| follows: | |||
| </p> | |||
| <ul> | |||
| <li><tt>|</tt> is an ordinary character, and there is no equivalent | |||
| for its functionality. <tt>+</tt>, and <tt>?</tt> are ordinary | |||
| characters.</li> | |||
| <li>The delimiters for bounds are <tt>\{</tt> and <tt>\}</tt>, with | |||
| <tt>{</tt> and <tt>}</tt> by themselves ordinary characters.</li> | |||
| <li>The parentheses for nested subexpressions are <tt>\(</tt> and | |||
| <tt>\)</tt>, with <tt>(</tt> and <tt>)</tt> by themselves ordinary | |||
| characters.</li> | |||
| <li><tt>^</tt> is an ordinary character except at the beginning of the | |||
| RE or the beginning of a parenthesized subexpression. Similarly, | |||
| <tt>$</tt> is an ordinary character except at the end of the | |||
| RE or the end of a parenthesized subexpression.</li> | |||
| </ul> | |||
| @@ -0,0 +1,34 @@ | |||
| ## Process this file with automake to produce Makefile.in | |||
| lib_LTLIBRARIES = libtre.la | |||
| libtre_la_LDFLAGS = -no-undefined -version-info 5:0:0 $(LDFLAGS) | |||
| libtre_la_LIBADD = $(LTLIBINTL) | |||
| noinst_HEADERS = \ | |||
| tre-ast.h \ | |||
| tre-compile.h \ | |||
| tre-internal.h \ | |||
| tre-match-utils.h \ | |||
| tre-mem.h \ | |||
| tre-parse.h \ | |||
| tre-stack.h \ | |||
| xmalloc.h | |||
| libtre_la_SOURCES = \ | |||
| tre-ast.c \ | |||
| tre-compile.c \ | |||
| tre-match-backtrack.c \ | |||
| tre-match-parallel.c \ | |||
| tre-mem.c \ | |||
| tre-parse.c \ | |||
| tre-stack.c \ | |||
| regcomp.c \ | |||
| regexec.c \ | |||
| regerror.c | |||
| if TRE_APPROX | |||
| libtre_la_SOURCES += tre-match-approx.c | |||
| endif TRE_APPROX | |||
| dist_pkginclude_HEADERS = tre.h regex.h | |||
| nodist_pkginclude_HEADERS = tre-config.h | |||
| @@ -0,0 +1,595 @@ | |||
| # Makefile.in generated by automake 1.10.1 from Makefile.am. | |||
| # @configure_input@ | |||
| # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, | |||
| # 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. | |||
| # This Makefile.in is free software; the Free Software Foundation | |||
| # gives unlimited permission to copy and/or distribute it, | |||
| # with or without modifications, as long as this notice is preserved. | |||
| # This program is distributed in the hope that it will be useful, | |||
| # but WITHOUT ANY WARRANTY, to the extent permitted by law; without | |||
| # even the implied warranty of MERCHANTABILITY or FITNESS FOR A | |||
| # PARTICULAR PURPOSE. | |||
| @SET_MAKE@ | |||
| VPATH = @srcdir@ | |||
| pkgdatadir = $(datadir)/@PACKAGE@ | |||
| pkglibdir = $(libdir)/@PACKAGE@ | |||
| pkgincludedir = $(includedir)/@PACKAGE@ | |||
| am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd | |||
| install_sh_DATA = $(install_sh) -c -m 644 | |||
| install_sh_PROGRAM = $(install_sh) -c | |||
| install_sh_SCRIPT = $(install_sh) -c | |||
| INSTALL_HEADER = $(INSTALL_DATA) | |||
| transform = $(program_transform_name) | |||
| NORMAL_INSTALL = : | |||
| PRE_INSTALL = : | |||
| POST_INSTALL = : | |||
| NORMAL_UNINSTALL = : | |||
| PRE_UNINSTALL = : | |||
| POST_UNINSTALL = : | |||
| build_triplet = @build@ | |||
| host_triplet = @host@ | |||
| target_triplet = @target@ | |||
| @TRE_APPROX_TRUE@am__append_1 = tre-match-approx.c | |||
| subdir = lib | |||
| DIST_COMMON = README $(dist_pkginclude_HEADERS) $(noinst_HEADERS) \ | |||
| $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ | |||
| $(srcdir)/tre-config.h.in | |||
| ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 | |||
| am__aclocal_m4_deps = $(top_srcdir)/m4/ac_libtool_tags.m4 \ | |||
| $(top_srcdir)/m4/ax_check_funcs_comp.m4 \ | |||
| $(top_srcdir)/m4/ax_check_sign.m4 \ | |||
| $(top_srcdir)/m4/ax_decl_wchar_max.m4 \ | |||
| $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ | |||
| $(top_srcdir)/m4/intlmacosx.m4 $(top_srcdir)/m4/lib-ld.m4 \ | |||
| $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ | |||
| $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ | |||
| $(top_srcdir)/m4/progtest.m4 \ | |||
| $(top_srcdir)/m4/vl_prog_cc_warnings.m4 \ | |||
| $(top_srcdir)/configure.ac | |||
| am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ | |||
| $(ACLOCAL_M4) | |||
| mkinstalldirs = $(SHELL) $(top_srcdir)/utils/mkinstalldirs | |||
| CONFIG_HEADER = $(top_builddir)/config.h tre-config.h | |||
| CONFIG_CLEAN_FILES = | |||
| am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; | |||
| am__vpath_adj = case $$p in \ | |||
| $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ | |||
| *) f=$$p;; \ | |||
| esac; | |||
| am__strip_dir = `echo $$p | sed -e 's|^.*/||'`; | |||
| am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(pkgincludedir)" \ | |||
| "$(DESTDIR)$(pkgincludedir)" | |||
| libLTLIBRARIES_INSTALL = $(INSTALL) | |||
| LTLIBRARIES = $(lib_LTLIBRARIES) | |||
| am__DEPENDENCIES_1 = | |||
| libtre_la_DEPENDENCIES = $(am__DEPENDENCIES_1) | |||
| am__libtre_la_SOURCES_DIST = tre-ast.c tre-compile.c \ | |||
| tre-match-backtrack.c tre-match-parallel.c tre-mem.c \ | |||
| tre-parse.c tre-stack.c regcomp.c regexec.c regerror.c \ | |||
| tre-match-approx.c | |||
| @TRE_APPROX_TRUE@am__objects_1 = tre-match-approx.lo | |||
| am_libtre_la_OBJECTS = tre-ast.lo tre-compile.lo \ | |||
| tre-match-backtrack.lo tre-match-parallel.lo tre-mem.lo \ | |||
| tre-parse.lo tre-stack.lo regcomp.lo regexec.lo regerror.lo \ | |||
| $(am__objects_1) | |||
| libtre_la_OBJECTS = $(am_libtre_la_OBJECTS) | |||
| libtre_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ | |||
| $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ | |||
| $(libtre_la_LDFLAGS) $(LDFLAGS) -o $@ | |||
| DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) | |||
| depcomp = $(SHELL) $(top_srcdir)/utils/depcomp | |||
| am__depfiles_maybe = depfiles | |||
| COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ | |||
| $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) | |||
| LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ | |||
| --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \ | |||
| $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) | |||
| CCLD = $(CC) | |||
| LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ | |||
| --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ | |||
| $(LDFLAGS) -o $@ | |||
| SOURCES = $(libtre_la_SOURCES) | |||
| DIST_SOURCES = $(am__libtre_la_SOURCES_DIST) | |||
| dist_pkgincludeHEADERS_INSTALL = $(INSTALL_HEADER) | |||
| nodist_pkgincludeHEADERS_INSTALL = $(INSTALL_HEADER) | |||
| HEADERS = $(dist_pkginclude_HEADERS) $(nodist_pkginclude_HEADERS) \ | |||
| $(noinst_HEADERS) | |||
| ETAGS = etags | |||
| CTAGS = ctags | |||
| DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) | |||
| ACLOCAL = @ACLOCAL@ | |||
| ALLOCA = @ALLOCA@ | |||
| AMTAR = @AMTAR@ | |||
| AR = @AR@ | |||
| AS = @AS@ | |||
| AUTOCONF = @AUTOCONF@ | |||
| AUTOHEADER = @AUTOHEADER@ | |||
| AUTOMAKE = @AUTOMAKE@ | |||
| AWK = @AWK@ | |||
| CC = @CC@ | |||
| CCDEPMODE = @CCDEPMODE@ | |||
| CFLAGS = @CFLAGS@ | |||
| CPP = @CPP@ | |||
| CPPFLAGS = @CPPFLAGS@ | |||
| CYGPATH_W = @CYGPATH_W@ | |||
| DEFS = @DEFS@ | |||
| DEPDIR = @DEPDIR@ | |||
| DLLTOOL = @DLLTOOL@ | |||
| DSYMUTIL = @DSYMUTIL@ | |||
| ECHO = @ECHO@ | |||
| ECHO_C = @ECHO_C@ | |||
| ECHO_N = @ECHO_N@ | |||
| ECHO_T = @ECHO_T@ | |||
| EGREP = @EGREP@ | |||
| EXEEXT = @EXEEXT@ | |||
| GETTEXT_MACRO_VERSION = @GETTEXT_MACRO_VERSION@ | |||
| GMSGFMT = @GMSGFMT@ | |||
| GMSGFMT_015 = @GMSGFMT_015@ | |||
| GREP = @GREP@ | |||
| INSTALL = @INSTALL@ | |||
| INSTALL_DATA = @INSTALL_DATA@ | |||
| INSTALL_PROGRAM = @INSTALL_PROGRAM@ | |||
| INSTALL_SCRIPT = @INSTALL_SCRIPT@ | |||
| INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ | |||
| INTLLIBS = @INTLLIBS@ | |||
| INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ | |||
| LDFLAGS = @LDFLAGS@ | |||
| LIBICONV = @LIBICONV@ | |||
| LIBINTL = @LIBINTL@ | |||
| LIBOBJS = @LIBOBJS@ | |||
| LIBS = @LIBS@ | |||
| LIBTOOL = @LIBTOOL@ | |||
| LN_S = @LN_S@ | |||
| LTLIBICONV = @LTLIBICONV@ | |||
| LTLIBINTL = @LTLIBINTL@ | |||
| LTLIBOBJS = @LTLIBOBJS@ | |||
| MAKEINFO = @MAKEINFO@ | |||
| MKDIR_P = @MKDIR_P@ | |||
| MSGFMT = @MSGFMT@ | |||
| MSGFMT_015 = @MSGFMT_015@ | |||
| MSGMERGE = @MSGMERGE@ | |||
| NMEDIT = @NMEDIT@ | |||
| OBJDUMP = @OBJDUMP@ | |||
| OBJEXT = @OBJEXT@ | |||
| PACKAGE = @PACKAGE@ | |||
| PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ | |||
| PACKAGE_NAME = @PACKAGE_NAME@ | |||
| PACKAGE_STRING = @PACKAGE_STRING@ | |||
| PACKAGE_TARNAME = @PACKAGE_TARNAME@ | |||
| PACKAGE_VERSION = @PACKAGE_VERSION@ | |||
| PATH_SEPARATOR = @PATH_SEPARATOR@ | |||
| POSUB = @POSUB@ | |||
| RANLIB = @RANLIB@ | |||
| SED = @SED@ | |||
| SET_MAKE = @SET_MAKE@ | |||
| SHELL = @SHELL@ | |||
| STRIP = @STRIP@ | |||
| TRE_VERSION = @TRE_VERSION@ | |||
| USE_NLS = @USE_NLS@ | |||
| VERSION = @VERSION@ | |||
| XGETTEXT = @XGETTEXT@ | |||
| XGETTEXT_015 = @XGETTEXT_015@ | |||
| XGETTEXT_EXTRA_OPTIONS = @XGETTEXT_EXTRA_OPTIONS@ | |||
| abs_builddir = @abs_builddir@ | |||
| abs_srcdir = @abs_srcdir@ | |||
| abs_top_builddir = @abs_top_builddir@ | |||
| abs_top_srcdir = @abs_top_srcdir@ | |||
| ac_ct_CC = @ac_ct_CC@ | |||
| am__include = @am__include@ | |||
| am__leading_dot = @am__leading_dot@ | |||
| am__quote = @am__quote@ | |||
| am__tar = @am__tar@ | |||
| am__untar = @am__untar@ | |||
| bindir = @bindir@ | |||
| build = @build@ | |||
| build_alias = @build_alias@ | |||
| build_cpu = @build_cpu@ | |||
| build_os = @build_os@ | |||
| build_vendor = @build_vendor@ | |||
| builddir = @builddir@ | |||
| datadir = @datadir@ | |||
| datarootdir = @datarootdir@ | |||
| docdir = @docdir@ | |||
| dvidir = @dvidir@ | |||
| exec_prefix = @exec_prefix@ | |||
| host = @host@ | |||
| host_alias = @host_alias@ | |||
| host_cpu = @host_cpu@ | |||
| host_os = @host_os@ | |||
| host_vendor = @host_vendor@ | |||
| htmldir = @htmldir@ | |||
| includedir = @includedir@ | |||
| infodir = @infodir@ | |||
| install_sh = @install_sh@ | |||
| libdir = @libdir@ | |||
| libexecdir = @libexecdir@ | |||
| localedir = @localedir@ | |||
| localstatedir = @localstatedir@ | |||
| mandir = @mandir@ | |||
| mkdir_p = @mkdir_p@ | |||
| oldincludedir = @oldincludedir@ | |||
| pdfdir = @pdfdir@ | |||
| prefix = @prefix@ | |||
| program_transform_name = @program_transform_name@ | |||
| psdir = @psdir@ | |||
| sbindir = @sbindir@ | |||
| sharedstatedir = @sharedstatedir@ | |||
| srcdir = @srcdir@ | |||
| sysconfdir = @sysconfdir@ | |||
| target = @target@ | |||
| target_alias = @target_alias@ | |||
| target_cpu = @target_cpu@ | |||
| target_os = @target_os@ | |||
| target_vendor = @target_vendor@ | |||
| top_builddir = @top_builddir@ | |||
| top_srcdir = @top_srcdir@ | |||
| lib_LTLIBRARIES = libtre.la | |||
| libtre_la_LDFLAGS = -no-undefined -version-info 5:0:0 $(LDFLAGS) | |||
| libtre_la_LIBADD = $(LTLIBINTL) | |||
| noinst_HEADERS = \ | |||
| tre-ast.h \ | |||
| tre-compile.h \ | |||
| tre-internal.h \ | |||
| tre-match-utils.h \ | |||
| tre-mem.h \ | |||
| tre-parse.h \ | |||
| tre-stack.h \ | |||
| xmalloc.h | |||
| libtre_la_SOURCES = tre-ast.c tre-compile.c tre-match-backtrack.c \ | |||
| tre-match-parallel.c tre-mem.c tre-parse.c tre-stack.c \ | |||
| regcomp.c regexec.c regerror.c $(am__append_1) | |||
| dist_pkginclude_HEADERS = tre.h regex.h | |||
| nodist_pkginclude_HEADERS = tre-config.h | |||
| all: tre-config.h | |||
| $(MAKE) $(AM_MAKEFLAGS) all-am | |||
| .SUFFIXES: | |||
| .SUFFIXES: .c .lo .o .obj | |||
| $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) | |||
| @for dep in $?; do \ | |||
| case '$(am__configure_deps)' in \ | |||
| *$$dep*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ | |||
| && exit 0; \ | |||
| exit 1;; \ | |||
| esac; \ | |||
| done; \ | |||
| echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign lib/Makefile'; \ | |||
| cd $(top_srcdir) && \ | |||
| $(AUTOMAKE) --foreign lib/Makefile | |||
| .PRECIOUS: Makefile | |||
| Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status | |||
| @case '$?' in \ | |||
| *config.status*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ | |||
| *) \ | |||
| echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ | |||
| cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ | |||
| esac; | |||
| $(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(top_srcdir)/configure: $(am__configure_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(ACLOCAL_M4): $(am__aclocal_m4_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| tre-config.h: stamp-h2 | |||
| @if test ! -f $@; then \ | |||
| rm -f stamp-h2; \ | |||
| $(MAKE) $(AM_MAKEFLAGS) stamp-h2; \ | |||
| else :; fi | |||
| stamp-h2: $(srcdir)/tre-config.h.in $(top_builddir)/config.status | |||
| @rm -f stamp-h2 | |||
| cd $(top_builddir) && $(SHELL) ./config.status lib/tre-config.h | |||
| $(srcdir)/tre-config.h.in: $(am__configure_deps) | |||
| cd $(top_srcdir) && $(AUTOHEADER) | |||
| rm -f stamp-h2 | |||
| touch $@ | |||
| distclean-hdr: | |||
| -rm -f tre-config.h stamp-h2 | |||
| install-libLTLIBRARIES: $(lib_LTLIBRARIES) | |||
| @$(NORMAL_INSTALL) | |||
| test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" | |||
| @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ | |||
| if test -f $$p; then \ | |||
| f=$(am__strip_dir) \ | |||
| echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(libLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) '$$p' '$(DESTDIR)$(libdir)/$$f'"; \ | |||
| $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(libLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) "$$p" "$(DESTDIR)$(libdir)/$$f"; \ | |||
| else :; fi; \ | |||
| done | |||
| uninstall-libLTLIBRARIES: | |||
| @$(NORMAL_UNINSTALL) | |||
| @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ | |||
| p=$(am__strip_dir) \ | |||
| echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(libdir)/$$p'"; \ | |||
| $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(libdir)/$$p"; \ | |||
| done | |||
| clean-libLTLIBRARIES: | |||
| -test -z "$(lib_LTLIBRARIES)" || rm -f $(lib_LTLIBRARIES) | |||
| @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ | |||
| dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \ | |||
| test "$$dir" != "$$p" || dir=.; \ | |||
| echo "rm -f \"$${dir}/so_locations\""; \ | |||
| rm -f "$${dir}/so_locations"; \ | |||
| done | |||
| libtre.la: $(libtre_la_OBJECTS) $(libtre_la_DEPENDENCIES) | |||
| $(libtre_la_LINK) -rpath $(libdir) $(libtre_la_OBJECTS) $(libtre_la_LIBADD) $(LIBS) | |||
| mostlyclean-compile: | |||
| -rm -f *.$(OBJEXT) | |||
| distclean-compile: | |||
| -rm -f *.tab.c | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regcomp.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regerror.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regexec.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-ast.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-compile.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-match-approx.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-match-backtrack.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-match-parallel.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-mem.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-parse.Plo@am__quote@ | |||
| @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tre-stack.Plo@am__quote@ | |||
| .c.o: | |||
| @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< | |||
| @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ | |||
| @am__fastdepCC_FALSE@ $(COMPILE) -c $< | |||
| .c.obj: | |||
| @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` | |||
| @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ | |||
| @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` | |||
| .c.lo: | |||
| @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< | |||
| @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ | |||
| @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ | |||
| @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< | |||
| mostlyclean-libtool: | |||
| -rm -f *.lo | |||
| clean-libtool: | |||
| -rm -rf .libs _libs | |||
| install-dist_pkgincludeHEADERS: $(dist_pkginclude_HEADERS) | |||
| @$(NORMAL_INSTALL) | |||
| test -z "$(pkgincludedir)" || $(MKDIR_P) "$(DESTDIR)$(pkgincludedir)" | |||
| @list='$(dist_pkginclude_HEADERS)'; for p in $$list; do \ | |||
| if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ | |||
| f=$(am__strip_dir) \ | |||
| echo " $(dist_pkgincludeHEADERS_INSTALL) '$$d$$p' '$(DESTDIR)$(pkgincludedir)/$$f'"; \ | |||
| $(dist_pkgincludeHEADERS_INSTALL) "$$d$$p" "$(DESTDIR)$(pkgincludedir)/$$f"; \ | |||
| done | |||
| uninstall-dist_pkgincludeHEADERS: | |||
| @$(NORMAL_UNINSTALL) | |||
| @list='$(dist_pkginclude_HEADERS)'; for p in $$list; do \ | |||
| f=$(am__strip_dir) \ | |||
| echo " rm -f '$(DESTDIR)$(pkgincludedir)/$$f'"; \ | |||
| rm -f "$(DESTDIR)$(pkgincludedir)/$$f"; \ | |||
| done | |||
| install-nodist_pkgincludeHEADERS: $(nodist_pkginclude_HEADERS) | |||
| @$(NORMAL_INSTALL) | |||
| test -z "$(pkgincludedir)" || $(MKDIR_P) "$(DESTDIR)$(pkgincludedir)" | |||
| @list='$(nodist_pkginclude_HEADERS)'; for p in $$list; do \ | |||
| if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ | |||
| f=$(am__strip_dir) \ | |||
| echo " $(nodist_pkgincludeHEADERS_INSTALL) '$$d$$p' '$(DESTDIR)$(pkgincludedir)/$$f'"; \ | |||
| $(nodist_pkgincludeHEADERS_INSTALL) "$$d$$p" "$(DESTDIR)$(pkgincludedir)/$$f"; \ | |||
| done | |||
| uninstall-nodist_pkgincludeHEADERS: | |||
| @$(NORMAL_UNINSTALL) | |||
| @list='$(nodist_pkginclude_HEADERS)'; for p in $$list; do \ | |||
| f=$(am__strip_dir) \ | |||
| echo " rm -f '$(DESTDIR)$(pkgincludedir)/$$f'"; \ | |||
| rm -f "$(DESTDIR)$(pkgincludedir)/$$f"; \ | |||
| done | |||
| ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) | |||
| list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| mkid -fID $$unique | |||
| tags: TAGS | |||
| TAGS: $(HEADERS) $(SOURCES) tre-config.h.in $(TAGS_DEPENDENCIES) \ | |||
| $(TAGS_FILES) $(LISP) | |||
| tags=; \ | |||
| here=`pwd`; \ | |||
| list='$(SOURCES) $(HEADERS) tre-config.h.in $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ | |||
| test -n "$$unique" || unique=$$empty_fix; \ | |||
| $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ | |||
| $$tags $$unique; \ | |||
| fi | |||
| ctags: CTAGS | |||
| CTAGS: $(HEADERS) $(SOURCES) tre-config.h.in $(TAGS_DEPENDENCIES) \ | |||
| $(TAGS_FILES) $(LISP) | |||
| tags=; \ | |||
| list='$(SOURCES) $(HEADERS) tre-config.h.in $(LISP) $(TAGS_FILES)'; \ | |||
| unique=`for i in $$list; do \ | |||
| if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ | |||
| done | \ | |||
| $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ | |||
| END { if (nonempty) { for (i in files) print i; }; }'`; \ | |||
| test -z "$(CTAGS_ARGS)$$tags$$unique" \ | |||
| || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ | |||
| $$tags $$unique | |||
| GTAGS: | |||
| here=`$(am__cd) $(top_builddir) && pwd` \ | |||
| && cd $(top_srcdir) \ | |||
| && gtags -i $(GTAGS_ARGS) $$here | |||
| distclean-tags: | |||
| -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags | |||
| distdir: $(DISTFILES) | |||
| @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| list='$(DISTFILES)'; \ | |||
| dist_files=`for file in $$list; do echo $$file; done | \ | |||
| sed -e "s|^$$srcdirstrip/||;t" \ | |||
| -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ | |||
| case $$dist_files in \ | |||
| */*) $(MKDIR_P) `echo "$$dist_files" | \ | |||
| sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ | |||
| sort -u` ;; \ | |||
| esac; \ | |||
| for file in $$dist_files; do \ | |||
| if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ | |||
| if test -d $$d/$$file; then \ | |||
| dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ | |||
| if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ | |||
| cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ | |||
| fi; \ | |||
| cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ | |||
| else \ | |||
| test -f $(distdir)/$$file \ | |||
| || cp -p $$d/$$file $(distdir)/$$file \ | |||
| || exit 1; \ | |||
| fi; \ | |||
| done | |||
| check-am: all-am | |||
| check: check-am | |||
| all-am: Makefile $(LTLIBRARIES) $(HEADERS) tre-config.h | |||
| installdirs: | |||
| for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(pkgincludedir)" "$(DESTDIR)$(pkgincludedir)"; do \ | |||
| test -z "$$dir" || $(MKDIR_P) "$$dir"; \ | |||
| done | |||
| install: install-am | |||
| install-exec: install-exec-am | |||
| install-data: install-data-am | |||
| uninstall: uninstall-am | |||
| install-am: all-am | |||
| @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am | |||
| installcheck: installcheck-am | |||
| install-strip: | |||
| $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ | |||
| install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ | |||
| `test -z '$(STRIP)' || \ | |||
| echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install | |||
| mostlyclean-generic: | |||
| clean-generic: | |||
| distclean-generic: | |||
| -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) | |||
| maintainer-clean-generic: | |||
| @echo "This command is intended for maintainers to use" | |||
| @echo "it deletes files that may require special tools to rebuild." | |||
| clean: clean-am | |||
| clean-am: clean-generic clean-libLTLIBRARIES clean-libtool \ | |||
| mostlyclean-am | |||
| distclean: distclean-am | |||
| -rm -rf ./$(DEPDIR) | |||
| -rm -f Makefile | |||
| distclean-am: clean-am distclean-compile distclean-generic \ | |||
| distclean-hdr distclean-tags | |||
| dvi: dvi-am | |||
| dvi-am: | |||
| html: html-am | |||
| info: info-am | |||
| info-am: | |||
| install-data-am: install-dist_pkgincludeHEADERS \ | |||
| install-nodist_pkgincludeHEADERS | |||
| install-dvi: install-dvi-am | |||
| install-exec-am: install-libLTLIBRARIES | |||
| install-html: install-html-am | |||
| install-info: install-info-am | |||
| install-man: | |||
| install-pdf: install-pdf-am | |||
| install-ps: install-ps-am | |||
| installcheck-am: | |||
| maintainer-clean: maintainer-clean-am | |||
| -rm -rf ./$(DEPDIR) | |||
| -rm -f Makefile | |||
| maintainer-clean-am: distclean-am maintainer-clean-generic | |||
| mostlyclean: mostlyclean-am | |||
| mostlyclean-am: mostlyclean-compile mostlyclean-generic \ | |||
| mostlyclean-libtool | |||
| pdf: pdf-am | |||
| pdf-am: | |||
| ps: ps-am | |||
| ps-am: | |||
| uninstall-am: uninstall-dist_pkgincludeHEADERS \ | |||
| uninstall-libLTLIBRARIES uninstall-nodist_pkgincludeHEADERS | |||
| .MAKE: install-am install-strip | |||
| .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ | |||
| clean-libLTLIBRARIES clean-libtool ctags distclean \ | |||
| distclean-compile distclean-generic distclean-hdr \ | |||
| distclean-libtool distclean-tags distdir dvi dvi-am html \ | |||
| html-am info info-am install install-am install-data \ | |||
| install-data-am install-dist_pkgincludeHEADERS install-dvi \ | |||
| install-dvi-am install-exec install-exec-am install-html \ | |||
| install-html-am install-info install-info-am \ | |||
| install-libLTLIBRARIES install-man \ | |||
| install-nodist_pkgincludeHEADERS install-pdf install-pdf-am \ | |||
| install-ps install-ps-am install-strip installcheck \ | |||
| installcheck-am installdirs maintainer-clean \ | |||
| maintainer-clean-generic mostlyclean mostlyclean-compile \ | |||
| mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ | |||
| tags uninstall uninstall-am uninstall-dist_pkgincludeHEADERS \ | |||
| uninstall-libLTLIBRARIES uninstall-nodist_pkgincludeHEADERS | |||
| # Tell versions [3.59,3.63) of GNU make to not export all variables. | |||
| # Otherwise a system limit (for SysV at least) may be exceeded. | |||
| .NOEXPORT: | |||
| @@ -0,0 +1,69 @@ | |||
| This code is structured roughly as follows: | |||
| xmalloc.c: | |||
| - Wrappers for the malloc() functions, for error generation and | |||
| memory leak checking purposes. | |||
| tre-mem.c: | |||
| - A simple and efficient memory allocator. | |||
| tre-stack.c: | |||
| - Implements a simple stack data structure. | |||
| tre-ast.c: | |||
| - Abstract syntax tree (AST) definitions. | |||
| tre-parse.c: | |||
| - Regexp parser. Parses a POSIX regexp (with TRE extensions) into | |||
| an abstract syntax tree (AST). | |||
| tre-compile.c: | |||
| - Compiles ASTs to ready-to-use regex objects. Comprised of two parts: | |||
| * Routine to convert an AST to a tagged AST. A tagged AST has | |||
| appropriate minimized or maximized tags added to keep track of | |||
| submatches. | |||
| * Routine to convert tagged ASTs to tagged nondeterministic state | |||
| machines (TNFAs) without epsilon transitions (transitions on | |||
| empty strings). | |||
| tre-match-parallel.c: | |||
| - Parallel TNFA matcher. | |||
| * The matcher basically takes a string and a TNFA and finds the | |||
| leftmost longest match and submatches in one pass over the input | |||
| string. Only the beginning of the input string is scanned until | |||
| a leftmost match and longest match is found. | |||
| * The matcher cannot handle back references, but the worst case | |||
| time consumption is O(l) where l is the length of the input | |||
| string. The space consumption is constant. | |||
| tre-match-backtrack.c: | |||
| - A traditional backtracking matcher. | |||
| * Like the parallel matcher, takes a string and a TNFA and finds | |||
| the leftmost longest match and submatches. Portions of the | |||
| input string may (and usually are) scanned multiple times. | |||
| * Can handle back references. The worst case time consumption, | |||
| however, is O(k^l) where k is some constant and l is the length | |||
| of the input string. The worst case space consumption is O(l). | |||
| tre-match-approx.c: | |||
| - Approximate parallel TNFA matcher. | |||
| * Finds the leftmost and longest match and submatches in one pass | |||
| over the input string. The match may contain errors. Each | |||
| missing, substituted, or extra character in the match increases | |||
| the cost of the match. A maximum cost for the returned match | |||
| can be given. The cost of the found match is returned. | |||
| * Cannot handle back references. The space and time consumption | |||
| bounds are the same as for the parallel exact matcher, but | |||
| in general this matcher is slower than the exact matcher. | |||
| regcomp.c: | |||
| - Implementation of the regcomp() family of functions as simple | |||
| wrappers for tre_compile(). | |||
| regexec.c: | |||
| - Implementation of the regexec() family of functions. | |||
| * The appropriate matcher is dispatched according to the | |||
| features used in the compiled regex object. | |||
| regerror.c: | |||
| - Implements the regerror() function. | |||
| @@ -0,0 +1,129 @@ | |||
| /* | |||
| tre_regcomp.c - TRE POSIX compatible regex compilation functions. | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <string.h> | |||
| #include <errno.h> | |||
| #include <stdlib.h> | |||
| #include "tre.h" | |||
| #include "tre-internal.h" | |||
| #include "xmalloc.h" | |||
| int | |||
| tre_regncomp(regex_t *preg, const char *regex, size_t n, int cflags) | |||
| { | |||
| int ret; | |||
| #if TRE_WCHAR | |||
| tre_char_t *wregex; | |||
| size_t wlen; | |||
| wregex = xmalloc(sizeof(tre_char_t) * (n + 1)); | |||
| if (wregex == NULL) | |||
| return REG_ESPACE; | |||
| /* If the current locale uses the standard single byte encoding of | |||
| characters, we don't do a multibyte string conversion. If we did, | |||
| many applications which use the default locale would break since | |||
| the default "C" locale uses the 7-bit ASCII character set, and | |||
| all characters with the eighth bit set would be considered invalid. */ | |||
| #if TRE_MULTIBYTE | |||
| if (TRE_MB_CUR_MAX == 1) | |||
| #endif /* TRE_MULTIBYTE */ | |||
| { | |||
| unsigned int i; | |||
| const unsigned char *str = (const unsigned char *)regex; | |||
| tre_char_t *wstr = wregex; | |||
| for (i = 0; i < n; i++) | |||
| *(wstr++) = *(str++); | |||
| wlen = n; | |||
| } | |||
| #if TRE_MULTIBYTE | |||
| else | |||
| { | |||
| int consumed; | |||
| tre_char_t *wcptr = wregex; | |||
| #ifdef HAVE_MBSTATE_T | |||
| mbstate_t state; | |||
| memset(&state, '\0', sizeof(state)); | |||
| #endif /* HAVE_MBSTATE_T */ | |||
| while (n > 0) | |||
| { | |||
| consumed = tre_mbrtowc(wcptr, regex, n, &state); | |||
| switch (consumed) | |||
| { | |||
| case 0: | |||
| if (*regex == '\0') | |||
| consumed = 1; | |||
| else | |||
| { | |||
| xfree(wregex); | |||
| return REG_BADPAT; | |||
| } | |||
| break; | |||
| case -1: | |||
| DPRINT(("mbrtowc: error %d: %s.\n", errno, strerror(errno))); | |||
| xfree(wregex); | |||
| return REG_BADPAT; | |||
| case -2: | |||
| /* The last character wasn't complete. Let's not call it a | |||
| fatal error. */ | |||
| consumed = n; | |||
| break; | |||
| } | |||
| regex += consumed; | |||
| n -= consumed; | |||
| wcptr++; | |||
| } | |||
| wlen = wcptr - wregex; | |||
| } | |||
| #endif /* TRE_MULTIBYTE */ | |||
| wregex[wlen] = L'\0'; | |||
| ret = tre_compile(preg, wregex, wlen, cflags); | |||
| xfree(wregex); | |||
| #else /* !TRE_WCHAR */ | |||
| ret = tre_compile(preg, (const tre_char_t *)regex, n, cflags); | |||
| #endif /* !TRE_WCHAR */ | |||
| return ret; | |||
| } | |||
| int | |||
| tre_regcomp(regex_t *preg, const char *regex, int cflags) | |||
| { | |||
| return tre_regncomp(preg, regex, regex ? strlen(regex) : 0, cflags); | |||
| } | |||
| #ifdef TRE_WCHAR | |||
| int | |||
| tre_regwncomp(regex_t *preg, const wchar_t *regex, size_t n, int cflags) | |||
| { | |||
| return tre_compile(preg, regex, n, cflags); | |||
| } | |||
| int | |||
| tre_regwcomp(regex_t *preg, const wchar_t *regex, int cflags) | |||
| { | |||
| return tre_compile(preg, regex, regex ? wcslen(regex) : 0, cflags); | |||
| } | |||
| #endif /* TRE_WCHAR */ | |||
| void | |||
| tre_regfree(regex_t *preg) | |||
| { | |||
| tre_free(preg); | |||
| } | |||
| /* EOF */ | |||
| @@ -0,0 +1,83 @@ | |||
| /* | |||
| tre_regerror.c - POSIX tre_regerror() implementation for TRE. | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <string.h> | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #include "tre-internal.h" | |||
| #include "tre.h" | |||
| #ifdef HAVE_GETTEXT | |||
| #include <libintl.h> | |||
| #else | |||
| #define dgettext(p, s) s | |||
| #define gettext(s) s | |||
| #endif | |||
| #define _(String) dgettext(PACKAGE, String) | |||
| #define gettext_noop(String) String | |||
| /* Error message strings for error codes listed in `tre.h'. This list | |||
| needs to be in sync with the codes listed there, naturally. */ | |||
| static const char *tre_error_messages[] = | |||
| { gettext_noop("No error"), /* REG_OK */ | |||
| gettext_noop("No match"), /* REG_NOMATCH */ | |||
| gettext_noop("Invalid regexp"), /* REG_BADPAT */ | |||
| gettext_noop("Unknown collating element"), /* REG_ECOLLATE */ | |||
| gettext_noop("Unknown character class name"), /* REG_ECTYPE */ | |||
| gettext_noop("Trailing backslash"), /* REG_EESCAPE */ | |||
| gettext_noop("Invalid back reference"), /* REG_ESUBREG */ | |||
| gettext_noop("Missing ']'"), /* REG_EBRACK */ | |||
| gettext_noop("Missing ')'"), /* REG_EPAREN */ | |||
| gettext_noop("Missing '}'"), /* REG_EBRACE */ | |||
| gettext_noop("Invalid contents of {}"), /* REG_BADBR */ | |||
| gettext_noop("Invalid character range"), /* REG_ERANGE */ | |||
| gettext_noop("Out of memory"), /* REG_ESPACE */ | |||
| gettext_noop("Invalid use of repetition operators") /* REG_BADRPT */ | |||
| }; | |||
| size_t | |||
| tre_regerror(int errcode, const regex_t *preg, char *errbuf, size_t errbuf_size) | |||
| { | |||
| const char *err; | |||
| size_t err_len; | |||
| /*LINTED*/(void)&preg; | |||
| if (errcode >= 0 | |||
| && errcode < (int)(sizeof(tre_error_messages) | |||
| / sizeof(*tre_error_messages))) | |||
| err = gettext(tre_error_messages[errcode]); | |||
| else | |||
| err = gettext("Unknown error"); | |||
| err_len = strlen(err) + 1; | |||
| if (errbuf_size > 0 && errbuf != NULL) | |||
| { | |||
| if (err_len > errbuf_size) | |||
| { | |||
| strncpy(errbuf, err, errbuf_size - 1); | |||
| errbuf[errbuf_size - 1] = '\0'; | |||
| } | |||
| else | |||
| { | |||
| strcpy(errbuf, err); | |||
| } | |||
| } | |||
| return err_len; | |||
| } | |||
| /* EOF */ | |||
| @@ -0,0 +1,38 @@ | |||
| /* | |||
| regex.h - TRE legacy API | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| This header is for source level compatibility with old code using | |||
| the <tre/regex.h> header which defined the TRE API functions without | |||
| a prefix. New code should include <tre/tre.h> instead. | |||
| */ | |||
| #ifndef TRE_REXEX_H | |||
| #define TRE_REGEX_H 1 | |||
| #include "tre.h" | |||
| #ifndef TRE_USE_SYSTEM_REGEX_H | |||
| #define regcomp tre_regcomp | |||
| #define regerror tre_regerror | |||
| #define regexec tre_regexec | |||
| #define regfree tre_regfree | |||
| #endif /* TRE_USE_SYSTEM_REGEX_H */ | |||
| #define regacomp tre_regacomp | |||
| #define regaexec tre_regaexec | |||
| #define regancomp tre_regancomp | |||
| #define reganexec tre_reganexec | |||
| #define regawncomp tre_regawncomp | |||
| #define regawnexec tre_regawnexec | |||
| #define regncomp tre_regncomp | |||
| #define regnexec tre_regnexec | |||
| #define regwcomp tre_regwcomp | |||
| #define regwexec tre_regwexec | |||
| #define regwncomp tre_regwncomp | |||
| #define regwnexec tre_regwnexec | |||
| #endif /* TRE_REGEX_H */ | |||
| @@ -0,0 +1,348 @@ | |||
| /* | |||
| tre_regexec.c - TRE POSIX compatible matching functions (and more). | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| /* AIX requires this to be the first thing in the file. */ | |||
| #ifndef __GNUC__ | |||
| # if HAVE_ALLOCA_H | |||
| # include <alloca.h> | |||
| # else | |||
| # ifdef _AIX | |||
| #pragma alloca | |||
| # else | |||
| # ifndef alloca /* predefined by HP cc +Olibcalls */ | |||
| char *alloca (); | |||
| # endif | |||
| # endif | |||
| # endif | |||
| #endif | |||
| #endif /* TRE_USE_ALLOCA */ | |||
| #include <assert.h> | |||
| #include <stdlib.h> | |||
| #include <string.h> | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #ifndef TRE_WCHAR | |||
| #include <ctype.h> | |||
| #endif /* !TRE_WCHAR */ | |||
| #ifdef HAVE_MALLOC_H | |||
| #include <malloc.h> | |||
| #endif /* HAVE_MALLOC_H */ | |||
| #include <limits.h> | |||
| #include "tre-internal.h" | |||
| #include "tre.h" | |||
| #include "xmalloc.h" | |||
| /* Fills the POSIX.2 regmatch_t array according to the TNFA tag and match | |||
| endpoint values. */ | |||
| void | |||
| tre_fill_pmatch(size_t nmatch, regmatch_t pmatch[], int cflags, | |||
| const tre_tnfa_t *tnfa, int *tags, int match_eo) | |||
| { | |||
| tre_submatch_data_t *submatch_data; | |||
| unsigned int i, j; | |||
| int *parents; | |||
| i = 0; | |||
| if (match_eo >= 0 && !(cflags & REG_NOSUB)) | |||
| { | |||
| /* Construct submatch offsets from the tags. */ | |||
| DPRINT(("end tag = t%d = %d\n", tnfa->end_tag, match_eo)); | |||
| submatch_data = tnfa->submatch_data; | |||
| while (i < tnfa->num_submatches && i < nmatch) | |||
| { | |||
| if (submatch_data[i].so_tag == tnfa->end_tag) | |||
| pmatch[i].rm_so = match_eo; | |||
| else | |||
| pmatch[i].rm_so = tags[submatch_data[i].so_tag]; | |||
| if (submatch_data[i].eo_tag == tnfa->end_tag) | |||
| pmatch[i].rm_eo = match_eo; | |||
| else | |||
| pmatch[i].rm_eo = tags[submatch_data[i].eo_tag]; | |||
| /* If either of the endpoints were not used, this submatch | |||
| was not part of the match. */ | |||
| if (pmatch[i].rm_so == -1 || pmatch[i].rm_eo == -1) | |||
| pmatch[i].rm_so = pmatch[i].rm_eo = -1; | |||
| DPRINT(("pmatch[%d] = {t%d = %d, t%d = %d}\n", i, | |||
| submatch_data[i].so_tag, pmatch[i].rm_so, | |||
| submatch_data[i].eo_tag, pmatch[i].rm_eo)); | |||
| i++; | |||
| } | |||
| /* Reset all submatches that are not within all of their parent | |||
| submatches. */ | |||
| i = 0; | |||
| while (i < tnfa->num_submatches && i < nmatch) | |||
| { | |||
| if (pmatch[i].rm_eo == -1) | |||
| assert(pmatch[i].rm_so == -1); | |||
| assert(pmatch[i].rm_so <= pmatch[i].rm_eo); | |||
| parents = submatch_data[i].parents; | |||
| if (parents != NULL) | |||
| for (j = 0; parents[j] >= 0; j++) | |||
| { | |||
| DPRINT(("pmatch[%d] parent %d\n", i, parents[j])); | |||
| if (pmatch[i].rm_so < pmatch[parents[j]].rm_so | |||
| || pmatch[i].rm_eo > pmatch[parents[j]].rm_eo) | |||
| pmatch[i].rm_so = pmatch[i].rm_eo = -1; | |||
| } | |||
| i++; | |||
| } | |||
| } | |||
| while (i < nmatch) | |||
| { | |||
| pmatch[i].rm_so = -1; | |||
| pmatch[i].rm_eo = -1; | |||
| i++; | |||
| } | |||
| } | |||
| /* | |||
| Wrapper functions for POSIX compatible regexp matching. | |||
| */ | |||
| int | |||
| tre_have_backrefs(const regex_t *preg) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| return tnfa->have_backrefs; | |||
| } | |||
| int | |||
| tre_have_approx(const regex_t *preg) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| return tnfa->have_approx; | |||
| } | |||
| static int | |||
| tre_match(const tre_tnfa_t *tnfa, const void *string, size_t len, | |||
| tre_str_type_t type, size_t nmatch, regmatch_t pmatch[], | |||
| int eflags) | |||
| { | |||
| reg_errcode_t status; | |||
| int *tags = NULL, eo; | |||
| if (tnfa->num_tags > 0 && nmatch > 0) | |||
| { | |||
| #ifdef TRE_USE_ALLOCA | |||
| tags = alloca(sizeof(*tags) * tnfa->num_tags); | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| tags = xmalloc(sizeof(*tags) * tnfa->num_tags); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| if (tags == NULL) | |||
| return REG_ESPACE; | |||
| } | |||
| /* Dispatch to the appropriate matcher. */ | |||
| if (tnfa->have_backrefs || eflags & REG_BACKTRACKING_MATCHER) | |||
| { | |||
| /* The regex has back references, use the backtracking matcher. */ | |||
| if (type == STR_USER) | |||
| { | |||
| const tre_str_source *source = string; | |||
| if (source->rewind == NULL || source->compare == NULL) | |||
| /* The backtracking matcher requires rewind and compare | |||
| capabilities from the input stream. */ | |||
| return REG_BADPAT; | |||
| } | |||
| status = tre_tnfa_run_backtrack(tnfa, string, (int)len, type, | |||
| tags, eflags, &eo); | |||
| } | |||
| #ifdef TRE_APPROX | |||
| else if (tnfa->have_approx || eflags & REG_APPROX_MATCHER) | |||
| { | |||
| /* The regex uses approximate matching, use the approximate matcher. */ | |||
| regamatch_t match; | |||
| regaparams_t params; | |||
| tre_regaparams_default(¶ms); | |||
| params.max_err = 0; | |||
| params.max_cost = 0; | |||
| status = tre_tnfa_run_approx(tnfa, string, (int)len, type, tags, | |||
| &match, params, eflags, &eo); | |||
| } | |||
| #endif /* TRE_APPROX */ | |||
| else | |||
| { | |||
| /* Exact matching, no back references, use the parallel matcher. */ | |||
| status = tre_tnfa_run_parallel(tnfa, string, (int)len, type, | |||
| tags, eflags, &eo); | |||
| } | |||
| if (status == REG_OK) | |||
| /* A match was found, so fill the submatch registers. */ | |||
| tre_fill_pmatch(nmatch, pmatch, tnfa->cflags, tnfa, tags, eo); | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (tags) | |||
| xfree(tags); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| return status; | |||
| } | |||
| int | |||
| tre_regnexec(const regex_t *preg, const char *str, size_t len, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| tre_str_type_t type = (TRE_MB_CUR_MAX == 1) ? STR_BYTE : STR_MBS; | |||
| return tre_match(tnfa, str, len, type, nmatch, pmatch, eflags); | |||
| } | |||
| int | |||
| tre_regexec(const regex_t *preg, const char *str, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags) | |||
| { | |||
| return tre_regnexec(preg, str, (unsigned)-1, nmatch, pmatch, eflags); | |||
| } | |||
| #ifdef TRE_WCHAR | |||
| int | |||
| tre_regwnexec(const regex_t *preg, const wchar_t *str, size_t len, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| return tre_match(tnfa, str, len, STR_WIDE, nmatch, pmatch, eflags); | |||
| } | |||
| int | |||
| tre_regwexec(const regex_t *preg, const wchar_t *str, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags) | |||
| { | |||
| return tre_regwnexec(preg, str, (unsigned)-1, nmatch, pmatch, eflags); | |||
| } | |||
| #endif /* TRE_WCHAR */ | |||
| int | |||
| tre_reguexec(const regex_t *preg, const tre_str_source *str, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| return tre_match(tnfa, str, (unsigned)-1, STR_USER, nmatch, pmatch, eflags); | |||
| } | |||
| #ifdef TRE_APPROX | |||
| /* | |||
| Wrapper functions for approximate regexp matching. | |||
| */ | |||
| static int | |||
| tre_match_approx(const tre_tnfa_t *tnfa, const void *string, size_t len, | |||
| tre_str_type_t type, regamatch_t *match, regaparams_t params, | |||
| int eflags) | |||
| { | |||
| reg_errcode_t status; | |||
| int *tags = NULL, eo; | |||
| /* If the regexp does not use approximate matching features, the | |||
| maximum cost is zero, and the approximate matcher isn't forced, | |||
| use the exact matcher instead. */ | |||
| if (params.max_cost == 0 && !tnfa->have_approx | |||
| && !(eflags & REG_APPROX_MATCHER)) | |||
| return tre_match(tnfa, string, len, type, match->nmatch, match->pmatch, | |||
| eflags); | |||
| /* Back references are not supported by the approximate matcher. */ | |||
| if (tnfa->have_backrefs) | |||
| return REG_BADPAT; | |||
| if (tnfa->num_tags > 0 && match->nmatch > 0) | |||
| { | |||
| #if TRE_USE_ALLOCA | |||
| tags = alloca(sizeof(*tags) * tnfa->num_tags); | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| tags = xmalloc(sizeof(*tags) * tnfa->num_tags); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| if (tags == NULL) | |||
| return REG_ESPACE; | |||
| } | |||
| status = tre_tnfa_run_approx(tnfa, string, (int)len, type, tags, | |||
| match, params, eflags, &eo); | |||
| if (status == REG_OK) | |||
| tre_fill_pmatch(match->nmatch, match->pmatch, tnfa->cflags, tnfa, tags, eo); | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (tags) | |||
| xfree(tags); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| return status; | |||
| } | |||
| int | |||
| tre_reganexec(const regex_t *preg, const char *str, size_t len, | |||
| regamatch_t *match, regaparams_t params, int eflags) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| tre_str_type_t type = (TRE_MB_CUR_MAX == 1) ? STR_BYTE : STR_MBS; | |||
| return tre_match_approx(tnfa, str, len, type, match, params, eflags); | |||
| } | |||
| int | |||
| tre_regaexec(const regex_t *preg, const char *str, | |||
| regamatch_t *match, regaparams_t params, int eflags) | |||
| { | |||
| return tre_reganexec(preg, str, (unsigned)-1, match, params, eflags); | |||
| } | |||
| #ifdef TRE_WCHAR | |||
| int | |||
| tre_regawnexec(const regex_t *preg, const wchar_t *str, size_t len, | |||
| regamatch_t *match, regaparams_t params, int eflags) | |||
| { | |||
| tre_tnfa_t *tnfa = (void *)preg->TRE_REGEX_T_FIELD; | |||
| return tre_match_approx(tnfa, str, len, STR_WIDE, | |||
| match, params, eflags); | |||
| } | |||
| int | |||
| tre_regawexec(const regex_t *preg, const wchar_t *str, | |||
| regamatch_t *match, regaparams_t params, int eflags) | |||
| { | |||
| return tre_regawnexec(preg, str, (unsigned)-1, match, params, eflags); | |||
| } | |||
| #endif /* TRE_WCHAR */ | |||
| void | |||
| tre_regaparams_default(regaparams_t *params) | |||
| { | |||
| memset(params, 0, sizeof(*params)); | |||
| params->cost_ins = 1; | |||
| params->cost_del = 1; | |||
| params->cost_subst = 1; | |||
| params->max_cost = INT_MAX; | |||
| params->max_ins = INT_MAX; | |||
| params->max_del = INT_MAX; | |||
| params->max_subst = INT_MAX; | |||
| params->max_err = INT_MAX; | |||
| } | |||
| #endif /* TRE_APPROX */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,226 @@ | |||
| /* | |||
| tre-ast.c - Abstract syntax tree (AST) routines | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <assert.h> | |||
| #include "tre-ast.h" | |||
| #include "tre-mem.h" | |||
| tre_ast_node_t * | |||
| tre_ast_new_node(tre_mem_t mem, tre_ast_type_t type, size_t size) | |||
| { | |||
| tre_ast_node_t *node; | |||
| node = tre_mem_calloc(mem, sizeof(*node)); | |||
| if (!node) | |||
| return NULL; | |||
| node->obj = tre_mem_calloc(mem, size); | |||
| if (!node->obj) | |||
| return NULL; | |||
| node->type = type; | |||
| node->nullable = -1; | |||
| node->submatch_id = -1; | |||
| return node; | |||
| } | |||
| tre_ast_node_t * | |||
| tre_ast_new_literal(tre_mem_t mem, int code_min, int code_max, int position) | |||
| { | |||
| tre_ast_node_t *node; | |||
| tre_literal_t *lit; | |||
| node = tre_ast_new_node(mem, LITERAL, sizeof(tre_literal_t)); | |||
| if (!node) | |||
| return NULL; | |||
| lit = node->obj; | |||
| lit->code_min = code_min; | |||
| lit->code_max = code_max; | |||
| lit->position = position; | |||
| return node; | |||
| } | |||
| tre_ast_node_t * | |||
| tre_ast_new_iter(tre_mem_t mem, tre_ast_node_t *arg, int min, int max, | |||
| int minimal) | |||
| { | |||
| tre_ast_node_t *node; | |||
| tre_iteration_t *iter; | |||
| node = tre_ast_new_node(mem, ITERATION, sizeof(tre_iteration_t)); | |||
| if (!node) | |||
| return NULL; | |||
| iter = node->obj; | |||
| iter->arg = arg; | |||
| iter->min = min; | |||
| iter->max = max; | |||
| iter->minimal = minimal; | |||
| node->num_submatches = arg->num_submatches; | |||
| return node; | |||
| } | |||
| tre_ast_node_t * | |||
| tre_ast_new_union(tre_mem_t mem, tre_ast_node_t *left, tre_ast_node_t *right) | |||
| { | |||
| tre_ast_node_t *node; | |||
| node = tre_ast_new_node(mem, UNION, sizeof(tre_union_t)); | |||
| if (node == NULL) | |||
| return NULL; | |||
| ((tre_union_t *)node->obj)->left = left; | |||
| ((tre_union_t *)node->obj)->right = right; | |||
| node->num_submatches = left->num_submatches + right->num_submatches; | |||
| return node; | |||
| } | |||
| tre_ast_node_t * | |||
| tre_ast_new_catenation(tre_mem_t mem, tre_ast_node_t *left, | |||
| tre_ast_node_t *right) | |||
| { | |||
| tre_ast_node_t *node; | |||
| node = tre_ast_new_node(mem, CATENATION, sizeof(tre_catenation_t)); | |||
| if (node == NULL) | |||
| return NULL; | |||
| ((tre_catenation_t *)node->obj)->left = left; | |||
| ((tre_catenation_t *)node->obj)->right = right; | |||
| node->num_submatches = left->num_submatches + right->num_submatches; | |||
| return node; | |||
| } | |||
| #ifdef TRE_DEBUG | |||
| static void | |||
| tre_findent(FILE *stream, int i) | |||
| { | |||
| while (i-- > 0) | |||
| fputc(' ', stream); | |||
| } | |||
| void | |||
| tre_print_params(int *params) | |||
| { | |||
| int i; | |||
| if (params) | |||
| { | |||
| DPRINT(("params [")); | |||
| for (i = 0; i < TRE_PARAM_LAST; i++) | |||
| { | |||
| if (params[i] == TRE_PARAM_UNSET) | |||
| DPRINT(("unset")); | |||
| else if (params[i] == TRE_PARAM_DEFAULT) | |||
| DPRINT(("default")); | |||
| else | |||
| DPRINT(("%d", params[i])); | |||
| if (i < TRE_PARAM_LAST - 1) | |||
| DPRINT((", ")); | |||
| } | |||
| DPRINT(("]")); | |||
| } | |||
| } | |||
| static void | |||
| tre_do_print(FILE *stream, tre_ast_node_t *ast, int indent) | |||
| { | |||
| int code_min, code_max, pos; | |||
| int num_tags = ast->num_tags; | |||
| tre_literal_t *lit; | |||
| tre_iteration_t *iter; | |||
| tre_findent(stream, indent); | |||
| switch (ast->type) | |||
| { | |||
| case LITERAL: | |||
| lit = ast->obj; | |||
| code_min = lit->code_min; | |||
| code_max = lit->code_max; | |||
| pos = lit->position; | |||
| if (IS_EMPTY(lit)) | |||
| { | |||
| fprintf(stream, "literal empty\n"); | |||
| } | |||
| else if (IS_ASSERTION(lit)) | |||
| { | |||
| int i; | |||
| char *assertions[] = { "bol", "eol", "ctype", "!ctype", | |||
| "bow", "eow", "wb", "!wb" }; | |||
| if (code_max >= ASSERT_LAST << 1) | |||
| assert(0); | |||
| fprintf(stream, "assertions: "); | |||
| for (i = 0; (1 << i) <= ASSERT_LAST; i++) | |||
| if (code_max & (1 << i)) | |||
| fprintf(stream, "%s ", assertions[i]); | |||
| fprintf(stream, "\n"); | |||
| } | |||
| else if (IS_TAG(lit)) | |||
| { | |||
| fprintf(stream, "tag %d\n", code_max); | |||
| } | |||
| else if (IS_BACKREF(lit)) | |||
| { | |||
| fprintf(stream, "backref %d, pos %d\n", code_max, pos); | |||
| } | |||
| else if (IS_PARAMETER(lit)) | |||
| { | |||
| tre_print_params(lit->u.params); | |||
| fprintf(stream, "\n"); | |||
| } | |||
| else | |||
| { | |||
| fprintf(stream, "literal (%c, %c) (%d, %d), pos %d, sub %d, " | |||
| "%d tags\n", code_min, code_max, code_min, code_max, pos, | |||
| ast->submatch_id, num_tags); | |||
| } | |||
| break; | |||
| case ITERATION: | |||
| iter = ast->obj; | |||
| fprintf(stream, "iteration {%d, %d}, sub %d, %d tags, %s\n", | |||
| iter->min, iter->max, ast->submatch_id, num_tags, | |||
| iter->minimal ? "minimal" : "greedy"); | |||
| tre_do_print(stream, iter->arg, indent + 2); | |||
| break; | |||
| case UNION: | |||
| fprintf(stream, "union, sub %d, %d tags\n", ast->submatch_id, num_tags); | |||
| tre_do_print(stream, ((tre_union_t *)ast->obj)->left, indent + 2); | |||
| tre_do_print(stream, ((tre_union_t *)ast->obj)->right, indent + 2); | |||
| break; | |||
| case CATENATION: | |||
| fprintf(stream, "catenation, sub %d, %d tags\n", ast->submatch_id, | |||
| num_tags); | |||
| tre_do_print(stream, ((tre_catenation_t *)ast->obj)->left, indent + 2); | |||
| tre_do_print(stream, ((tre_catenation_t *)ast->obj)->right, indent + 2); | |||
| break; | |||
| default: | |||
| assert(0); | |||
| break; | |||
| } | |||
| } | |||
| static void | |||
| tre_ast_fprint(FILE *stream, tre_ast_node_t *ast) | |||
| { | |||
| tre_do_print(stream, ast, 0); | |||
| } | |||
| void | |||
| tre_ast_print(tre_ast_node_t *tree) | |||
| { | |||
| printf("AST:\n"); | |||
| tre_ast_fprint(stdout, tree); | |||
| } | |||
| #endif /* TRE_DEBUG */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,128 @@ | |||
| /* | |||
| tre-ast.h - Abstract syntax tree (AST) definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_AST_H | |||
| #define TRE_AST_H 1 | |||
| #include "tre-mem.h" | |||
| #include "tre-internal.h" | |||
| #include "tre-compile.h" | |||
| /* The different AST node types. */ | |||
| typedef enum { | |||
| LITERAL, | |||
| CATENATION, | |||
| ITERATION, | |||
| UNION | |||
| } tre_ast_type_t; | |||
| /* Special subtypes of TRE_LITERAL. */ | |||
| #define EMPTY -1 /* Empty leaf (denotes empty string). */ | |||
| #define ASSERTION -2 /* Assertion leaf. */ | |||
| #define TAG -3 /* Tag leaf. */ | |||
| #define BACKREF -4 /* Back reference leaf. */ | |||
| #define PARAMETER -5 /* Parameter. */ | |||
| #define IS_SPECIAL(x) ((x)->code_min < 0) | |||
| #define IS_EMPTY(x) ((x)->code_min == EMPTY) | |||
| #define IS_ASSERTION(x) ((x)->code_min == ASSERTION) | |||
| #define IS_TAG(x) ((x)->code_min == TAG) | |||
| #define IS_BACKREF(x) ((x)->code_min == BACKREF) | |||
| #define IS_PARAMETER(x) ((x)->code_min == PARAMETER) | |||
| /* A generic AST node. All AST nodes consist of this node on the top | |||
| level with `obj' pointing to the actual content. */ | |||
| typedef struct { | |||
| tre_ast_type_t type; /* Type of the node. */ | |||
| void *obj; /* Pointer to actual node. */ | |||
| int nullable; | |||
| int submatch_id; | |||
| int num_submatches; | |||
| int num_tags; | |||
| tre_pos_and_tags_t *firstpos; | |||
| tre_pos_and_tags_t *lastpos; | |||
| } tre_ast_node_t; | |||
| /* A "literal" node. These are created for assertions, back references, | |||
| tags, matching parameter settings, and all expressions that match one | |||
| character. */ | |||
| typedef struct { | |||
| long code_min; | |||
| long code_max; | |||
| int position; | |||
| union { | |||
| tre_ctype_t class; | |||
| int *params; | |||
| } u; | |||
| tre_ctype_t *neg_classes; | |||
| } tre_literal_t; | |||
| /* A "catenation" node. These are created when two regexps are concatenated. | |||
| If there are more than one subexpressions in sequence, the `left' part | |||
| holds all but the last, and `right' part holds the last subexpression | |||
| (catenation is left associative). */ | |||
| typedef struct { | |||
| tre_ast_node_t *left; | |||
| tre_ast_node_t *right; | |||
| } tre_catenation_t; | |||
| /* An "iteration" node. These are created for the "*", "+", "?", and "{m,n}" | |||
| operators. */ | |||
| typedef struct { | |||
| /* Subexpression to match. */ | |||
| tre_ast_node_t *arg; | |||
| /* Minimum number of consecutive matches. */ | |||
| int min; | |||
| /* Maximum number of consecutive matches. */ | |||
| int max; | |||
| /* If 0, match as many characters as possible, if 1 match as few as | |||
| possible. Note that this does not always mean the same thing as | |||
| matching as many/few repetitions as possible. */ | |||
| unsigned int minimal:1; | |||
| /* Approximate matching parameters (or NULL). */ | |||
| int *params; | |||
| } tre_iteration_t; | |||
| /* An "union" node. These are created for the "|" operator. */ | |||
| typedef struct { | |||
| tre_ast_node_t *left; | |||
| tre_ast_node_t *right; | |||
| } tre_union_t; | |||
| tre_ast_node_t * | |||
| tre_ast_new_node(tre_mem_t mem, tre_ast_type_t type, size_t size); | |||
| tre_ast_node_t * | |||
| tre_ast_new_literal(tre_mem_t mem, int code_min, int code_max, int position); | |||
| tre_ast_node_t * | |||
| tre_ast_new_iter(tre_mem_t mem, tre_ast_node_t *arg, int min, int max, | |||
| int minimal); | |||
| tre_ast_node_t * | |||
| tre_ast_new_union(tre_mem_t mem, tre_ast_node_t *left, tre_ast_node_t *right); | |||
| tre_ast_node_t * | |||
| tre_ast_new_catenation(tre_mem_t mem, tre_ast_node_t *left, | |||
| tre_ast_node_t *right); | |||
| #ifdef TRE_DEBUG | |||
| void | |||
| tre_ast_print(tre_ast_node_t *tree); | |||
| /* XXX - rethink AST printing API */ | |||
| void | |||
| tre_print_params(int *params); | |||
| #endif /* TRE_DEBUG */ | |||
| #endif /* TRE_AST_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,27 @@ | |||
| /* | |||
| tre-compile.h: Regex compilation definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_COMPILE_H | |||
| #define TRE_COMPILE_H 1 | |||
| typedef struct { | |||
| int position; | |||
| int code_min; | |||
| int code_max; | |||
| int *tags; | |||
| int assertions; | |||
| tre_ctype_t class; | |||
| tre_ctype_t *neg_classes; | |||
| int backref; | |||
| int *params; | |||
| } tre_pos_and_tags_t; | |||
| #endif /* TRE_COMPILE_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,43 @@ | |||
| /* tre-config.h.in. This file has all definitions that are needed in | |||
| `tre.h'. Note that this file must contain only the bare minimum | |||
| of definitions without the TRE_ prefix to avoid conflicts between | |||
| definitions here and definitions included from somewhere else. */ | |||
| /* Define to 1 if you have the <libutf8.h> header file. */ | |||
| #undef HAVE_LIBUTF8_H | |||
| /* Define to 1 if the system has the type `reg_errcode_t'. */ | |||
| #undef HAVE_REG_ERRCODE_T | |||
| /* Define to 1 if you have the <sys/types.h> header file. */ | |||
| #undef HAVE_SYS_TYPES_H | |||
| /* Define to 1 if you have the <wchar.h> header file. */ | |||
| #undef HAVE_WCHAR_H | |||
| /* Define if you want to enable approximate matching functionality. */ | |||
| #undef TRE_APPROX | |||
| /* Define to enable multibyte character set support. */ | |||
| #undef TRE_MULTIBYTE | |||
| /* Define to the absolute path to the system tre.h */ | |||
| #undef TRE_SYSTEM_REGEX_H_PATH | |||
| /* Define to include the system regex.h from tre.h */ | |||
| #undef TRE_USE_SYSTEM_REGEX_H | |||
| /* Define to enable wide character (wchar_t) support. */ | |||
| #undef TRE_WCHAR | |||
| /* TRE version string. */ | |||
| #undef TRE_VERSION | |||
| /* TRE version level 1. */ | |||
| #undef TRE_VERSION_1 | |||
| /* TRE version level 2. */ | |||
| #undef TRE_VERSION_2 | |||
| /* TRE version level 3. */ | |||
| #undef TRE_VERSION_3 | |||
| @@ -0,0 +1,287 @@ | |||
| /* | |||
| tre-internal.h - TRE internal definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_INTERNAL_H | |||
| #define TRE_INTERNAL_H 1 | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* !HAVE_WCTYPE_H */ | |||
| #include <ctype.h> | |||
| #include "tre.h" | |||
| #ifdef TRE_DEBUG | |||
| #include <stdio.h> | |||
| #define DPRINT(msg) do {printf msg; fflush(stdout);} while(/*CONSTCOND*/0) | |||
| #else /* !TRE_DEBUG */ | |||
| #define DPRINT(msg) do { } while(/*CONSTCOND*/0) | |||
| #endif /* !TRE_DEBUG */ | |||
| #define elementsof(x) ( sizeof(x) / sizeof(x[0]) ) | |||
| #ifdef HAVE_MBRTOWC | |||
| #define tre_mbrtowc(pwc, s, n, ps) (mbrtowc((pwc), (s), (n), (ps))) | |||
| #else /* !HAVE_MBRTOWC */ | |||
| #ifdef HAVE_MBTOWC | |||
| #define tre_mbrtowc(pwc, s, n, ps) (mbtowc((pwc), (s), (n))) | |||
| #endif /* HAVE_MBTOWC */ | |||
| #endif /* !HAVE_MBRTOWC */ | |||
| #ifdef TRE_MULTIBYTE | |||
| #ifdef HAVE_MBSTATE_T | |||
| #define TRE_MBSTATE | |||
| #endif /* TRE_MULTIBYTE */ | |||
| #endif /* HAVE_MBSTATE_T */ | |||
| /* Define the character types and functions. */ | |||
| #ifdef TRE_WCHAR | |||
| /* Wide characters. */ | |||
| typedef wint_t tre_cint_t; | |||
| #define TRE_CHAR_MAX WCHAR_MAX | |||
| #ifdef TRE_MULTIBYTE | |||
| #define TRE_MB_CUR_MAX MB_CUR_MAX | |||
| #else /* !TRE_MULTIBYTE */ | |||
| #define TRE_MB_CUR_MAX 1 | |||
| #endif /* !TRE_MULTIBYTE */ | |||
| #define tre_isalnum iswalnum | |||
| #define tre_isalpha iswalpha | |||
| #ifdef HAVE_ISWBLANK | |||
| #define tre_isblank iswblank | |||
| #endif /* HAVE_ISWBLANK */ | |||
| #define tre_iscntrl iswcntrl | |||
| #define tre_isdigit iswdigit | |||
| #define tre_isgraph iswgraph | |||
| #define tre_islower iswlower | |||
| #define tre_isprint iswprint | |||
| #define tre_ispunct iswpunct | |||
| #define tre_isspace iswspace | |||
| #define tre_isupper iswupper | |||
| #define tre_isxdigit iswxdigit | |||
| #define tre_tolower towlower | |||
| #define tre_toupper towupper | |||
| #define tre_strlen wcslen | |||
| #else /* !TRE_WCHAR */ | |||
| /* 8 bit characters. */ | |||
| typedef short tre_cint_t; | |||
| #define TRE_CHAR_MAX 255 | |||
| #define TRE_MB_CUR_MAX 1 | |||
| #define tre_isalnum isalnum | |||
| #define tre_isalpha isalpha | |||
| #ifdef HAVE_ISASCII | |||
| #define tre_isascii isascii | |||
| #endif /* HAVE_ISASCII */ | |||
| #ifdef HAVE_ISBLANK | |||
| #define tre_isblank isblank | |||
| #endif /* HAVE_ISBLANK */ | |||
| #define tre_iscntrl iscntrl | |||
| #define tre_isdigit isdigit | |||
| #define tre_isgraph isgraph | |||
| #define tre_islower islower | |||
| #define tre_isprint isprint | |||
| #define tre_ispunct ispunct | |||
| #define tre_isspace isspace | |||
| #define tre_isupper isupper | |||
| #define tre_isxdigit isxdigit | |||
| #define tre_tolower(c) (tre_cint_t)(tolower(c)) | |||
| #define tre_toupper(c) (tre_cint_t)(toupper(c)) | |||
| #define tre_strlen(s) (strlen((const char*)s)) | |||
| #endif /* !TRE_WCHAR */ | |||
| #if defined(TRE_WCHAR) && defined(HAVE_ISWCTYPE) && defined(HAVE_WCTYPE) | |||
| #define TRE_USE_SYSTEM_WCTYPE 1 | |||
| #endif | |||
| #ifdef TRE_USE_SYSTEM_WCTYPE | |||
| /* Use system provided iswctype() and wctype(). */ | |||
| typedef wctype_t tre_ctype_t; | |||
| #define tre_isctype iswctype | |||
| #define tre_ctype wctype | |||
| #else /* !TRE_USE_SYSTEM_WCTYPE */ | |||
| /* Define our own versions of iswctype() and wctype(). */ | |||
| typedef int (*tre_ctype_t)(tre_cint_t); | |||
| #define tre_isctype(c, type) ( (type)(c) ) | |||
| tre_ctype_t tre_ctype(const char *name); | |||
| #endif /* !TRE_USE_SYSTEM_WCTYPE */ | |||
| typedef enum { STR_WIDE, STR_BYTE, STR_MBS, STR_USER } tre_str_type_t; | |||
| /* Returns number of bytes to add to (char *)ptr to make it | |||
| properly aligned for the type. */ | |||
| #define ALIGN(ptr, type) \ | |||
| ((((long)ptr) % sizeof(type)) \ | |||
| ? (sizeof(type) - (((long)ptr) % sizeof(type))) \ | |||
| : 0) | |||
| #undef MAX | |||
| #undef MIN | |||
| #define MAX(a, b) (((a) >= (b)) ? (a) : (b)) | |||
| #define MIN(a, b) (((a) <= (b)) ? (a) : (b)) | |||
| /* Define STRF to the correct printf formatter for strings. */ | |||
| #ifdef TRE_WCHAR | |||
| #define STRF "ls" | |||
| #else /* !TRE_WCHAR */ | |||
| #define STRF "s" | |||
| #endif /* !TRE_WCHAR */ | |||
| /* TNFA transition type. A TNFA state is an array of transitions, | |||
| the terminator is a transition with NULL `state'. */ | |||
| typedef struct tnfa_transition tre_tnfa_transition_t; | |||
| struct tnfa_transition { | |||
| /* Range of accepted characters. */ | |||
| tre_cint_t code_min; | |||
| tre_cint_t code_max; | |||
| /* Pointer to the destination state. */ | |||
| tre_tnfa_transition_t *state; | |||
| /* ID number of the destination state. */ | |||
| int state_id; | |||
| /* -1 terminated array of tags (or NULL). */ | |||
| int *tags; | |||
| /* Matching parameters settings (or NULL). */ | |||
| int *params; | |||
| /* Assertion bitmap. */ | |||
| int assertions; | |||
| /* Assertion parameters. */ | |||
| union { | |||
| /* Character class assertion. */ | |||
| tre_ctype_t class; | |||
| /* Back reference assertion. */ | |||
| int backref; | |||
| } u; | |||
| /* Negative character class assertions. */ | |||
| tre_ctype_t *neg_classes; | |||
| }; | |||
| /* Assertions. */ | |||
| #define ASSERT_AT_BOL 1 /* Beginning of line. */ | |||
| #define ASSERT_AT_EOL 2 /* End of line. */ | |||
| #define ASSERT_CHAR_CLASS 4 /* Character class in `class'. */ | |||
| #define ASSERT_CHAR_CLASS_NEG 8 /* Character classes in `neg_classes'. */ | |||
| #define ASSERT_AT_BOW 16 /* Beginning of word. */ | |||
| #define ASSERT_AT_EOW 32 /* End of word. */ | |||
| #define ASSERT_AT_WB 64 /* Word boundary. */ | |||
| #define ASSERT_AT_WB_NEG 128 /* Not a word boundary. */ | |||
| #define ASSERT_BACKREF 256 /* A back reference in `backref'. */ | |||
| #define ASSERT_LAST 256 | |||
| /* Tag directions. */ | |||
| typedef enum { | |||
| TRE_TAG_MINIMIZE = 0, | |||
| TRE_TAG_MAXIMIZE = 1 | |||
| } tre_tag_direction_t; | |||
| /* Parameters that can be changed dynamically while matching. */ | |||
| typedef enum { | |||
| TRE_PARAM_COST_INS = 0, | |||
| TRE_PARAM_COST_DEL = 1, | |||
| TRE_PARAM_COST_SUBST = 2, | |||
| TRE_PARAM_COST_MAX = 3, | |||
| TRE_PARAM_MAX_INS = 4, | |||
| TRE_PARAM_MAX_DEL = 5, | |||
| TRE_PARAM_MAX_SUBST = 6, | |||
| TRE_PARAM_MAX_ERR = 7, | |||
| TRE_PARAM_DEPTH = 8, | |||
| TRE_PARAM_LAST = 9 | |||
| } tre_param_t; | |||
| /* Unset matching parameter */ | |||
| #define TRE_PARAM_UNSET -1 | |||
| /* Signifies the default matching parameter value. */ | |||
| #define TRE_PARAM_DEFAULT -2 | |||
| /* Instructions to compute submatch register values from tag values | |||
| after a successful match. */ | |||
| struct tre_submatch_data { | |||
| /* Tag that gives the value for rm_so (submatch start offset). */ | |||
| int so_tag; | |||
| /* Tag that gives the value for rm_eo (submatch end offset). */ | |||
| int eo_tag; | |||
| /* List of submatches this submatch is contained in. */ | |||
| int *parents; | |||
| }; | |||
| typedef struct tre_submatch_data tre_submatch_data_t; | |||
| /* TNFA definition. */ | |||
| typedef struct tnfa tre_tnfa_t; | |||
| struct tnfa { | |||
| tre_tnfa_transition_t *transitions; | |||
| unsigned int num_transitions; | |||
| tre_tnfa_transition_t *initial; | |||
| tre_tnfa_transition_t *final; | |||
| tre_submatch_data_t *submatch_data; | |||
| char *firstpos_chars; | |||
| int first_char; | |||
| unsigned int num_submatches; | |||
| tre_tag_direction_t *tag_directions; | |||
| int *minimal_tags; | |||
| int num_tags; | |||
| int num_minimals; | |||
| int end_tag; | |||
| int num_states; | |||
| int cflags; | |||
| int have_backrefs; | |||
| int have_approx; | |||
| int params_depth; | |||
| }; | |||
| int | |||
| tre_compile(regex_t *preg, const tre_char_t *regex, size_t n, int cflags); | |||
| void | |||
| tre_free(regex_t *preg); | |||
| void | |||
| tre_fill_pmatch(size_t nmatch, regmatch_t pmatch[], int cflags, | |||
| const tre_tnfa_t *tnfa, int *tags, int match_eo); | |||
| reg_errcode_t | |||
| tre_tnfa_run_parallel(const tre_tnfa_t *tnfa, const void *string, int len, | |||
| tre_str_type_t type, int *match_tags, int eflags, | |||
| int *match_end_ofs); | |||
| reg_errcode_t | |||
| tre_tnfa_run_parallel(const tre_tnfa_t *tnfa, const void *string, int len, | |||
| tre_str_type_t type, int *match_tags, int eflags, | |||
| int *match_end_ofs); | |||
| reg_errcode_t | |||
| tre_tnfa_run_backtrack(const tre_tnfa_t *tnfa, const void *string, | |||
| int len, tre_str_type_t type, int *match_tags, | |||
| int eflags, int *match_end_ofs); | |||
| #ifdef TRE_APPROX | |||
| reg_errcode_t | |||
| tre_tnfa_run_approx(const tre_tnfa_t *tnfa, const void *string, int len, | |||
| tre_str_type_t type, int *match_tags, | |||
| regamatch_t *match, regaparams_t params, | |||
| int eflags, int *match_end_ofs); | |||
| #endif /* TRE_APPROX */ | |||
| #endif /* TRE_INTERNAL_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,812 @@ | |||
| /* | |||
| tre-match-approx.c - TRE approximate regex matching engine | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| /* AIX requires this to be the first thing in the file. */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| #ifndef __GNUC__ | |||
| # if HAVE_ALLOCA_H | |||
| # include <alloca.h> | |||
| # else | |||
| # ifdef _AIX | |||
| #pragma alloca | |||
| # else | |||
| # ifndef alloca /* predefined by HP cc +Olibcalls */ | |||
| char *alloca (); | |||
| # endif | |||
| # endif | |||
| # endif | |||
| #endif | |||
| #endif /* TRE_USE_ALLOCA */ | |||
| #define __USE_STRING_INLINES | |||
| #undef __NO_INLINE__ | |||
| #include <assert.h> | |||
| #include <stdlib.h> | |||
| #include <string.h> | |||
| #include <limits.h> | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #ifndef TRE_WCHAR | |||
| #include <ctype.h> | |||
| #endif /* !TRE_WCHAR */ | |||
| #ifdef HAVE_MALLOC_H | |||
| #include <malloc.h> | |||
| #endif /* HAVE_MALLOC_H */ | |||
| #include "tre-internal.h" | |||
| #include "tre-match-utils.h" | |||
| #include "tre.h" | |||
| #include "xmalloc.h" | |||
| #define TRE_M_COST 0 | |||
| #define TRE_M_NUM_INS 1 | |||
| #define TRE_M_NUM_DEL 2 | |||
| #define TRE_M_NUM_SUBST 3 | |||
| #define TRE_M_NUM_ERR 4 | |||
| #define TRE_M_LAST 5 | |||
| #define TRE_M_MAX_DEPTH 3 | |||
| typedef struct { | |||
| /* State in the TNFA transition table. */ | |||
| tre_tnfa_transition_t *state; | |||
| /* Position in input string. */ | |||
| int pos; | |||
| /* Tag values. */ | |||
| int *tags; | |||
| /* Matching parameters. */ | |||
| regaparams_t params; | |||
| /* Nesting depth of parameters. This is used as an index in | |||
| the `costs' array. */ | |||
| int depth; | |||
| /* Costs and counter values for different parameter nesting depths. */ | |||
| int costs[TRE_M_MAX_DEPTH + 1][TRE_M_LAST]; | |||
| } tre_tnfa_approx_reach_t; | |||
| #ifdef TRE_DEBUG | |||
| /* Prints the `reach' array in a readable fashion with DPRINT. */ | |||
| static void | |||
| tre_print_reach(const tre_tnfa_t *tnfa, tre_tnfa_approx_reach_t *reach, | |||
| int pos, int num_tags) | |||
| { | |||
| int id; | |||
| /* Print each state on one line. */ | |||
| DPRINT((" reach:\n")); | |||
| for (id = 0; id < tnfa->num_states; id++) | |||
| { | |||
| int i, j; | |||
| if (reach[id].pos < pos) | |||
| continue; /* Not reached. */ | |||
| DPRINT((" %03d, costs ", id)); | |||
| for (i = 0; i <= reach[id].depth; i++) | |||
| { | |||
| DPRINT(("[")); | |||
| for (j = 0; j < TRE_M_LAST; j++) | |||
| { | |||
| DPRINT(("%2d", reach[id].costs[i][j])); | |||
| if (j + 1 < TRE_M_LAST) | |||
| DPRINT((",")); | |||
| } | |||
| DPRINT(("]")); | |||
| if (i + 1 <= reach[id].depth) | |||
| DPRINT((", ")); | |||
| } | |||
| DPRINT(("\n tags ")); | |||
| for (i = 0; i < num_tags; i++) | |||
| { | |||
| DPRINT(("%02d", reach[id].tags[i])); | |||
| if (i + 1 < num_tags) | |||
| DPRINT((",")); | |||
| } | |||
| DPRINT(("\n")); | |||
| } | |||
| DPRINT(("\n")); | |||
| } | |||
| #endif /* TRE_DEBUG */ | |||
| /* Sets the matching parameters in `reach' to the ones defined in the `pa' | |||
| array. If `pa' specifies default values, they are taken from | |||
| `default_params'. */ | |||
| inline static void | |||
| tre_set_params(tre_tnfa_approx_reach_t *reach, | |||
| int *pa, regaparams_t default_params) | |||
| { | |||
| int value; | |||
| /* If depth is increased reset costs and counters to zero for the | |||
| new levels. */ | |||
| value = pa[TRE_PARAM_DEPTH]; | |||
| assert(value <= TRE_M_MAX_DEPTH); | |||
| if (value > reach->depth) | |||
| { | |||
| int i, j; | |||
| for (i = reach->depth + 1; i <= value; i++) | |||
| for (j = 0; j < TRE_M_LAST; j++) | |||
| reach->costs[i][j] = 0; | |||
| } | |||
| reach->depth = value; | |||
| /* Set insert cost. */ | |||
| value = pa[TRE_PARAM_COST_INS]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.cost_ins = default_params.cost_ins; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.cost_ins = value; | |||
| /* Set delete cost. */ | |||
| value = pa[TRE_PARAM_COST_DEL]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.cost_del = default_params.cost_del; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.cost_del = value; | |||
| /* Set substitute cost. */ | |||
| value = pa[TRE_PARAM_COST_SUBST]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.cost_subst = default_params.cost_subst; | |||
| else | |||
| reach->params.cost_subst = value; | |||
| /* Set maximum cost. */ | |||
| value = pa[TRE_PARAM_COST_MAX]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.max_cost = default_params.max_cost; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.max_cost = value; | |||
| /* Set maximum inserts. */ | |||
| value = pa[TRE_PARAM_MAX_INS]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.max_ins = default_params.max_ins; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.max_ins = value; | |||
| /* Set maximum deletes. */ | |||
| value = pa[TRE_PARAM_MAX_DEL]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.max_del = default_params.max_del; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.max_del = value; | |||
| /* Set maximum substitutes. */ | |||
| value = pa[TRE_PARAM_MAX_SUBST]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.max_subst = default_params.max_subst; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.max_subst = value; | |||
| /* Set maximum number of errors. */ | |||
| value = pa[TRE_PARAM_MAX_ERR]; | |||
| if (value == TRE_PARAM_DEFAULT) | |||
| reach->params.max_err = default_params.max_err; | |||
| else if (value != TRE_PARAM_UNSET) | |||
| reach->params.max_err = value; | |||
| } | |||
| reg_errcode_t | |||
| tre_tnfa_run_approx(const tre_tnfa_t *tnfa, const void *string, int len, | |||
| tre_str_type_t type, int *match_tags, | |||
| regamatch_t *match, regaparams_t default_params, | |||
| int eflags, int *match_end_ofs) | |||
| { | |||
| /* State variables required by GET_NEXT_WCHAR. */ | |||
| tre_char_t prev_c = 0, next_c = 0; | |||
| const char *str_byte = string; | |||
| int pos = -1; | |||
| unsigned int pos_add_next = 1; | |||
| #ifdef TRE_WCHAR | |||
| const wchar_t *str_wide = string; | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_t mbstate; | |||
| #endif /* !TRE_WCHAR */ | |||
| #endif /* TRE_WCHAR */ | |||
| int reg_notbol = eflags & REG_NOTBOL; | |||
| int reg_noteol = eflags & REG_NOTEOL; | |||
| int reg_newline = tnfa->cflags & REG_NEWLINE; | |||
| int str_user_end = 0; | |||
| int prev_pos; | |||
| /* Number of tags. */ | |||
| int num_tags; | |||
| /* The reach tables. */ | |||
| tre_tnfa_approx_reach_t *reach, *reach_next; | |||
| /* Tag array for temporary use. */ | |||
| int *tmp_tags; | |||
| /* End offset of best match so far, or -1 if no match found yet. */ | |||
| int match_eo = -1; | |||
| /* Costs of the match. */ | |||
| int match_costs[TRE_M_LAST]; | |||
| /* Space for temporary data required for matching. */ | |||
| unsigned char *buf; | |||
| int i, id; | |||
| if (!match_tags) | |||
| num_tags = 0; | |||
| else | |||
| num_tags = tnfa->num_tags; | |||
| #ifdef TRE_MBSTATE | |||
| memset(&mbstate, '\0', sizeof(mbstate)); | |||
| #endif /* TRE_MBSTATE */ | |||
| DPRINT(("tre_tnfa_run_approx, input type %d, len %d, eflags %d, " | |||
| "match_tags %p\n", | |||
| type, len, eflags, | |||
| match_tags)); | |||
| DPRINT(("max cost %d, ins %d, del %d, subst %d\n", | |||
| default_params.max_cost, | |||
| default_params.cost_ins, | |||
| default_params.cost_del, | |||
| default_params.cost_subst)); | |||
| /* Allocate memory for temporary data required for matching. This needs to | |||
| be done for every matching operation to be thread safe. This allocates | |||
| everything in a single large block from the stack frame using alloca() | |||
| or with malloc() if alloca is unavailable. */ | |||
| { | |||
| unsigned char *buf_cursor; | |||
| /* Space needed for one array of tags. */ | |||
| int tag_bytes = sizeof(*tmp_tags) * num_tags; | |||
| /* Space needed for one reach table. */ | |||
| int reach_bytes = sizeof(*reach_next) * tnfa->num_states; | |||
| /* Total space needed. */ | |||
| int total_bytes = reach_bytes * 2 + (tnfa->num_states * 2 + 1 ) * tag_bytes; | |||
| /* Add some extra to make sure we can align the pointers. The multiplier | |||
| used here must be equal to the number of ALIGN calls below. */ | |||
| total_bytes += (sizeof(long) - 1) * 3; | |||
| /* Allocate the memory. */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| buf = alloca(total_bytes); | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| buf = xmalloc((unsigned)total_bytes); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| if (!buf) | |||
| return REG_ESPACE; | |||
| memset(buf, 0, (size_t)total_bytes); | |||
| /* Allocate `tmp_tags' from `buf'. */ | |||
| tmp_tags = (void *)buf; | |||
| buf_cursor = buf + tag_bytes; | |||
| buf_cursor += ALIGN(buf_cursor, long); | |||
| /* Allocate `reach' from `buf'. */ | |||
| reach = (void *)buf_cursor; | |||
| buf_cursor += reach_bytes; | |||
| buf_cursor += ALIGN(buf_cursor, long); | |||
| /* Allocate `reach_next' from `buf'. */ | |||
| reach_next = (void *)buf_cursor; | |||
| buf_cursor += reach_bytes; | |||
| buf_cursor += ALIGN(buf_cursor, long); | |||
| /* Allocate tag arrays for `reach' and `reach_next' from `buf'. */ | |||
| for (i = 0; i < tnfa->num_states; i++) | |||
| { | |||
| reach[i].tags = (void *)buf_cursor; | |||
| buf_cursor += tag_bytes; | |||
| reach_next[i].tags = (void *)buf_cursor; | |||
| buf_cursor += tag_bytes; | |||
| } | |||
| assert(buf_cursor <= buf + total_bytes); | |||
| } | |||
| for (i = 0; i < TRE_M_LAST; i++) | |||
| match_costs[i] = INT_MAX; | |||
| /* Mark the reach arrays empty. */ | |||
| for (i = 0; i < tnfa->num_states; i++) | |||
| reach[i].pos = reach_next[i].pos = -2; | |||
| prev_pos = pos; | |||
| GET_NEXT_WCHAR(); | |||
| pos = 0; | |||
| while (/*CONSTCOND*/1) | |||
| { | |||
| DPRINT(("%03d:%2lc/%05d\n", pos, (tre_cint_t)next_c, (int)next_c)); | |||
| /* Add initial states to `reach_next' if an exact match has not yet | |||
| been found. */ | |||
| if (match_costs[TRE_M_COST] > 0) | |||
| { | |||
| tre_tnfa_transition_t *trans; | |||
| DPRINT((" init")); | |||
| for (trans = tnfa->initial; trans->state; trans++) | |||
| { | |||
| int stateid = trans->state_id; | |||
| /* If this state is not currently in `reach_next', add it | |||
| there. */ | |||
| if (reach_next[stateid].pos < pos) | |||
| { | |||
| if (trans->assertions && CHECK_ASSERTIONS(trans->assertions)) | |||
| { | |||
| /* Assertions failed, don't add this state. */ | |||
| DPRINT((" !%d (assert)", stateid)); | |||
| continue; | |||
| } | |||
| DPRINT((" %d", stateid)); | |||
| reach_next[stateid].state = trans->state; | |||
| reach_next[stateid].pos = pos; | |||
| /* Compute tag values after this transition. */ | |||
| for (i = 0; i < num_tags; i++) | |||
| reach_next[stateid].tags[i] = -1; | |||
| if (trans->tags) | |||
| for (i = 0; trans->tags[i] >= 0; i++) | |||
| if (trans->tags[i] < num_tags) | |||
| reach_next[stateid].tags[trans->tags[i]] = pos; | |||
| /* Set the parameters, depth, and costs. */ | |||
| reach_next[stateid].params = default_params; | |||
| reach_next[stateid].depth = 0; | |||
| for (i = 0; i < TRE_M_LAST; i++) | |||
| reach_next[stateid].costs[0][i] = 0; | |||
| if (trans->params) | |||
| tre_set_params(&reach_next[stateid], trans->params, | |||
| default_params); | |||
| /* If this is the final state, mark the exact match. */ | |||
| if (trans->state == tnfa->final) | |||
| { | |||
| match_eo = pos; | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = reach_next[stateid].tags[i]; | |||
| for (i = 0; i < TRE_M_LAST; i++) | |||
| match_costs[i] = 0; | |||
| } | |||
| } | |||
| } | |||
| DPRINT(("\n")); | |||
| } | |||
| /* Handle inserts. This is done by pretending there's an epsilon | |||
| transition from each state in `reach' back to the same state. | |||
| We don't need to worry about the final state here; this will never | |||
| give a better match than what we already have. */ | |||
| for (id = 0; id < tnfa->num_states; id++) | |||
| { | |||
| int depth; | |||
| int cost, cost0; | |||
| if (reach[id].pos != prev_pos) | |||
| { | |||
| DPRINT((" insert: %d not reached\n", id)); | |||
| continue; /* Not reached. */ | |||
| } | |||
| depth = reach[id].depth; | |||
| /* Compute and check cost at current depth. */ | |||
| cost = reach[id].costs[depth][TRE_M_COST]; | |||
| if (reach[id].params.cost_ins != TRE_PARAM_UNSET) | |||
| cost += reach[id].params.cost_ins; | |||
| if (cost > reach[id].params.max_cost) | |||
| continue; /* Cost too large. */ | |||
| /* Check number of inserts at current depth. */ | |||
| if (reach[id].costs[depth][TRE_M_NUM_INS] + 1 | |||
| > reach[id].params.max_ins) | |||
| continue; /* Too many inserts. */ | |||
| /* Check total number of errors at current depth. */ | |||
| if (reach[id].costs[depth][TRE_M_NUM_ERR] + 1 | |||
| > reach[id].params.max_err) | |||
| continue; /* Too many errors. */ | |||
| /* Compute overall cost. */ | |||
| cost0 = cost; | |||
| if (depth > 0) | |||
| { | |||
| cost0 = reach[id].costs[0][TRE_M_COST]; | |||
| if (reach[id].params.cost_ins != TRE_PARAM_UNSET) | |||
| cost0 += reach[id].params.cost_ins; | |||
| else | |||
| cost0 += default_params.cost_ins; | |||
| } | |||
| DPRINT((" insert: from %d to %d, cost %d: ", id, id, | |||
| reach[id].costs[depth][TRE_M_COST])); | |||
| if (reach_next[id].pos == pos | |||
| && (cost0 >= reach_next[id].costs[0][TRE_M_COST])) | |||
| { | |||
| DPRINT(("lose\n")); | |||
| continue; | |||
| } | |||
| DPRINT(("win\n")); | |||
| /* Copy state, position, tags, parameters, and depth. */ | |||
| reach_next[id].state = reach[id].state; | |||
| reach_next[id].pos = pos; | |||
| for (i = 0; i < num_tags; i++) | |||
| reach_next[id].tags[i] = reach[id].tags[i]; | |||
| reach_next[id].params = reach[id].params; | |||
| reach_next[id].depth = reach[id].depth; | |||
| /* Set the costs after this transition. */ | |||
| memcpy(reach_next[id].costs, reach[id].costs, | |||
| sizeof(reach_next[id].costs[0][0]) | |||
| * TRE_M_LAST * (depth + 1)); | |||
| reach_next[id].costs[depth][TRE_M_COST] = cost; | |||
| reach_next[id].costs[depth][TRE_M_NUM_INS]++; | |||
| reach_next[id].costs[depth][TRE_M_NUM_ERR]++; | |||
| if (depth > 0) | |||
| { | |||
| reach_next[id].costs[0][TRE_M_COST] = cost0; | |||
| reach_next[id].costs[0][TRE_M_NUM_INS]++; | |||
| reach_next[id].costs[0][TRE_M_NUM_ERR]++; | |||
| } | |||
| } | |||
| /* Handle deletes. This is done by traversing through the whole TNFA | |||
| pretending that all transitions are epsilon transitions, until | |||
| no more states can be reached with better costs. */ | |||
| { | |||
| /* XXX - dynamic ringbuffer size */ | |||
| tre_tnfa_approx_reach_t *ringbuffer[512]; | |||
| tre_tnfa_approx_reach_t **deque_start, **deque_end; | |||
| deque_start = deque_end = ringbuffer; | |||
| /* Add all states in `reach_next' to the deque. */ | |||
| for (id = 0; id < tnfa->num_states; id++) | |||
| { | |||
| if (reach_next[id].pos != pos) | |||
| continue; | |||
| *deque_end = &reach_next[id]; | |||
| deque_end++; | |||
| assert(deque_end != deque_start); | |||
| } | |||
| /* Repeat until the deque is empty. */ | |||
| while (deque_end != deque_start) | |||
| { | |||
| tre_tnfa_approx_reach_t *reach_p; | |||
| int depth; | |||
| int cost, cost0; | |||
| tre_tnfa_transition_t *trans; | |||
| /* Pop the first item off the deque. */ | |||
| reach_p = *deque_start; | |||
| id = reach_p - reach_next; | |||
| depth = reach_p->depth; | |||
| /* Compute cost at current depth. */ | |||
| cost = reach_p->costs[depth][TRE_M_COST]; | |||
| if (reach_p->params.cost_del != TRE_PARAM_UNSET) | |||
| cost += reach_p->params.cost_del; | |||
| /* Check cost, number of deletes, and total number of errors | |||
| at current depth. */ | |||
| if (cost > reach_p->params.max_cost | |||
| || (reach_p->costs[depth][TRE_M_NUM_DEL] + 1 | |||
| > reach_p->params.max_del) | |||
| || (reach_p->costs[depth][TRE_M_NUM_ERR] + 1 | |||
| > reach_p->params.max_err)) | |||
| { | |||
| /* Too many errors or cost too large. */ | |||
| DPRINT((" delete: from %03d: cost too large\n", id)); | |||
| deque_start++; | |||
| if (deque_start >= (ringbuffer + 512)) | |||
| deque_start = ringbuffer; | |||
| continue; | |||
| } | |||
| /* Compute overall cost. */ | |||
| cost0 = cost; | |||
| if (depth > 0) | |||
| { | |||
| cost0 = reach_p->costs[0][TRE_M_COST]; | |||
| if (reach_p->params.cost_del != TRE_PARAM_UNSET) | |||
| cost0 += reach_p->params.cost_del; | |||
| else | |||
| cost0 += default_params.cost_del; | |||
| } | |||
| for (trans = reach_p->state; trans->state; trans++) | |||
| { | |||
| int dest_id = trans->state_id; | |||
| DPRINT((" delete: from %03d to %03d, cost %d (%d): ", | |||
| id, dest_id, cost0, reach_p->params.max_cost)); | |||
| if (trans->assertions && CHECK_ASSERTIONS(trans->assertions)) | |||
| { | |||
| DPRINT(("assertion failed\n")); | |||
| continue; | |||
| } | |||
| /* Compute tag values after this transition. */ | |||
| for (i = 0; i < num_tags; i++) | |||
| tmp_tags[i] = reach_p->tags[i]; | |||
| if (trans->tags) | |||
| for (i = 0; trans->tags[i] >= 0; i++) | |||
| if (trans->tags[i] < num_tags) | |||
| tmp_tags[trans->tags[i]] = pos; | |||
| /* If another path has also reached this state, choose the one | |||
| with the smallest cost or best tags if costs are equal. */ | |||
| if (reach_next[dest_id].pos == pos | |||
| && (cost0 > reach_next[dest_id].costs[0][TRE_M_COST] | |||
| || (cost0 == reach_next[dest_id].costs[0][TRE_M_COST] | |||
| && (!match_tags | |||
| || !tre_tag_order(num_tags, | |||
| tnfa->tag_directions, | |||
| tmp_tags, | |||
| reach_next[dest_id].tags))))) | |||
| { | |||
| DPRINT(("lose, cost0 %d, have %d\n", | |||
| cost0, reach_next[dest_id].costs[0][TRE_M_COST])); | |||
| continue; | |||
| } | |||
| DPRINT(("win\n")); | |||
| /* Set state, position, tags, parameters, depth, and costs. */ | |||
| reach_next[dest_id].state = trans->state; | |||
| reach_next[dest_id].pos = pos; | |||
| for (i = 0; i < num_tags; i++) | |||
| reach_next[dest_id].tags[i] = tmp_tags[i]; | |||
| reach_next[dest_id].params = reach_p->params; | |||
| if (trans->params) | |||
| tre_set_params(&reach_next[dest_id], trans->params, | |||
| default_params); | |||
| reach_next[dest_id].depth = reach_p->depth; | |||
| memcpy(&reach_next[dest_id].costs, | |||
| reach_p->costs, | |||
| sizeof(reach_p->costs[0][0]) | |||
| * TRE_M_LAST * (depth + 1)); | |||
| reach_next[dest_id].costs[depth][TRE_M_COST] = cost; | |||
| reach_next[dest_id].costs[depth][TRE_M_NUM_DEL]++; | |||
| reach_next[dest_id].costs[depth][TRE_M_NUM_ERR]++; | |||
| if (depth > 0) | |||
| { | |||
| reach_next[dest_id].costs[0][TRE_M_COST] = cost0; | |||
| reach_next[dest_id].costs[0][TRE_M_NUM_DEL]++; | |||
| reach_next[dest_id].costs[0][TRE_M_NUM_ERR]++; | |||
| } | |||
| if (trans->state == tnfa->final | |||
| && (match_eo < 0 | |||
| || match_costs[TRE_M_COST] > cost0 | |||
| || (match_costs[TRE_M_COST] == cost0 | |||
| && (num_tags > 0 | |||
| && tmp_tags[0] <= match_tags[0])))) | |||
| { | |||
| DPRINT((" setting new match at %d, cost %d\n", | |||
| pos, cost0)); | |||
| match_eo = pos; | |||
| memcpy(match_costs, reach_next[dest_id].costs[0], | |||
| sizeof(match_costs[0]) * TRE_M_LAST); | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = tmp_tags[i]; | |||
| } | |||
| /* Add to the end of the deque. */ | |||
| *deque_end = &reach_next[dest_id]; | |||
| deque_end++; | |||
| if (deque_end >= (ringbuffer + 512)) | |||
| deque_end = ringbuffer; | |||
| assert(deque_end != deque_start); | |||
| } | |||
| deque_start++; | |||
| if (deque_start >= (ringbuffer + 512)) | |||
| deque_start = ringbuffer; | |||
| } | |||
| } | |||
| #ifdef TRE_DEBUG | |||
| tre_print_reach(tnfa, reach_next, pos, num_tags); | |||
| #endif /* TRE_DEBUG */ | |||
| /* Check for end of string. */ | |||
| if (len < 0) | |||
| { | |||
| if (type == STR_USER) | |||
| { | |||
| if (str_user_end) | |||
| break; | |||
| } | |||
| else if (next_c == L'\0') | |||
| break; | |||
| } | |||
| else | |||
| { | |||
| if (pos >= len) | |||
| break; | |||
| } | |||
| prev_pos = pos; | |||
| GET_NEXT_WCHAR(); | |||
| /* Swap `reach' and `reach_next'. */ | |||
| { | |||
| tre_tnfa_approx_reach_t *tmp; | |||
| tmp = reach; | |||
| reach = reach_next; | |||
| reach_next = tmp; | |||
| } | |||
| /* Handle exact matches and substitutions. */ | |||
| for (id = 0; id < tnfa->num_states; id++) | |||
| { | |||
| tre_tnfa_transition_t *trans; | |||
| if (reach[id].pos < prev_pos) | |||
| continue; /* Not reached. */ | |||
| for (trans = reach[id].state; trans->state; trans++) | |||
| { | |||
| int dest_id; | |||
| int depth; | |||
| int cost, cost0, err; | |||
| if (trans->assertions | |||
| && (CHECK_ASSERTIONS(trans->assertions) | |||
| || CHECK_CHAR_CLASSES(trans, tnfa, eflags))) | |||
| { | |||
| DPRINT((" exact, from %d: assert failed\n", id)); | |||
| continue; | |||
| } | |||
| depth = reach[id].depth; | |||
| dest_id = trans->state_id; | |||
| cost = reach[id].costs[depth][TRE_M_COST]; | |||
| cost0 = reach[id].costs[0][TRE_M_COST]; | |||
| err = 0; | |||
| if (trans->code_min > (tre_cint_t)prev_c | |||
| || trans->code_max < (tre_cint_t)prev_c) | |||
| { | |||
| /* Handle substitutes. The required character was not in | |||
| the string, so match it in place of whatever was supposed | |||
| to be there and increase costs accordingly. */ | |||
| err = 1; | |||
| /* Compute and check cost at current depth. */ | |||
| cost = reach[id].costs[depth][TRE_M_COST]; | |||
| if (reach[id].params.cost_subst != TRE_PARAM_UNSET) | |||
| cost += reach[id].params.cost_subst; | |||
| if (cost > reach[id].params.max_cost) | |||
| continue; /* Cost too large. */ | |||
| /* Check number of substitutes at current depth. */ | |||
| if (reach[id].costs[depth][TRE_M_NUM_SUBST] + 1 | |||
| > reach[id].params.max_subst) | |||
| continue; /* Too many substitutes. */ | |||
| /* Check total number of errors at current depth. */ | |||
| if (reach[id].costs[depth][TRE_M_NUM_ERR] + 1 | |||
| > reach[id].params.max_err) | |||
| continue; /* Too many errors. */ | |||
| /* Compute overall cost. */ | |||
| cost0 = cost; | |||
| if (depth > 0) | |||
| { | |||
| cost0 = reach[id].costs[0][TRE_M_COST]; | |||
| if (reach[id].params.cost_subst != TRE_PARAM_UNSET) | |||
| cost0 += reach[id].params.cost_subst; | |||
| else | |||
| cost0 += default_params.cost_subst; | |||
| } | |||
| DPRINT((" subst, from %03d to %03d, cost %d: ", | |||
| id, dest_id, cost0)); | |||
| } | |||
| else | |||
| DPRINT((" exact, from %03d to %03d, cost %d: ", | |||
| id, dest_id, cost0)); | |||
| /* Compute tag values after this transition. */ | |||
| for (i = 0; i < num_tags; i++) | |||
| tmp_tags[i] = reach[id].tags[i]; | |||
| if (trans->tags) | |||
| for (i = 0; trans->tags[i] >= 0; i++) | |||
| if (trans->tags[i] < num_tags) | |||
| tmp_tags[trans->tags[i]] = pos; | |||
| /* If another path has also reached this state, choose the | |||
| one with the smallest cost or best tags if costs are equal. */ | |||
| if (reach_next[dest_id].pos == pos | |||
| && (cost0 > reach_next[dest_id].costs[0][TRE_M_COST] | |||
| || (cost0 == reach_next[dest_id].costs[0][TRE_M_COST] | |||
| && !tre_tag_order(num_tags, tnfa->tag_directions, | |||
| tmp_tags, | |||
| reach_next[dest_id].tags)))) | |||
| { | |||
| DPRINT(("lose\n")); | |||
| continue; | |||
| } | |||
| DPRINT(("win %d %d\n", | |||
| reach_next[dest_id].pos, | |||
| reach_next[dest_id].costs[0][TRE_M_COST])); | |||
| /* Set state, position, tags, and depth. */ | |||
| reach_next[dest_id].state = trans->state; | |||
| reach_next[dest_id].pos = pos; | |||
| for (i = 0; i < num_tags; i++) | |||
| reach_next[dest_id].tags[i] = tmp_tags[i]; | |||
| reach_next[dest_id].depth = reach[id].depth; | |||
| /* Set parameters. */ | |||
| reach_next[dest_id].params = reach[id].params; | |||
| if (trans->params) | |||
| tre_set_params(&reach_next[dest_id], trans->params, | |||
| default_params); | |||
| /* Set the costs after this transition. */ | |||
| memcpy(&reach_next[dest_id].costs, | |||
| reach[id].costs, | |||
| sizeof(reach[id].costs[0][0]) | |||
| * TRE_M_LAST * (depth + 1)); | |||
| reach_next[dest_id].costs[depth][TRE_M_COST] = cost; | |||
| reach_next[dest_id].costs[depth][TRE_M_NUM_SUBST] += err; | |||
| reach_next[dest_id].costs[depth][TRE_M_NUM_ERR] += err; | |||
| if (depth > 0) | |||
| { | |||
| reach_next[dest_id].costs[0][TRE_M_COST] = cost0; | |||
| reach_next[dest_id].costs[0][TRE_M_NUM_SUBST] += err; | |||
| reach_next[dest_id].costs[0][TRE_M_NUM_ERR] += err; | |||
| } | |||
| if (trans->state == tnfa->final | |||
| && (match_eo < 0 | |||
| || cost0 < match_costs[TRE_M_COST] | |||
| || (cost0 == match_costs[TRE_M_COST] | |||
| && num_tags > 0 && tmp_tags[0] <= match_tags[0]))) | |||
| { | |||
| DPRINT((" setting new match at %d, cost %d\n", | |||
| pos, cost0)); | |||
| match_eo = pos; | |||
| for (i = 0; i < TRE_M_LAST; i++) | |||
| match_costs[i] = reach_next[dest_id].costs[0][i]; | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = tmp_tags[i]; | |||
| } | |||
| } | |||
| } | |||
| } | |||
| DPRINT(("match end offset = %d, match cost = %d\n", match_eo, | |||
| match_costs[TRE_M_COST])); | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (buf) | |||
| xfree(buf); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| match->cost = match_costs[TRE_M_COST]; | |||
| match->num_ins = match_costs[TRE_M_NUM_INS]; | |||
| match->num_del = match_costs[TRE_M_NUM_DEL]; | |||
| match->num_subst = match_costs[TRE_M_NUM_SUBST]; | |||
| *match_end_ofs = match_eo; | |||
| return match_eo >= 0 ? REG_OK : REG_NOMATCH; | |||
| } | |||
| @@ -0,0 +1,666 @@ | |||
| /* | |||
| tre-match-backtrack.c - TRE backtracking regex matching engine | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| /* | |||
| This matcher is for regexps that use back referencing. Regexp matching | |||
| with back referencing is an NP-complete problem on the number of back | |||
| references. The easiest way to match them is to use a backtracking | |||
| routine which basically goes through all possible paths in the TNFA | |||
| and chooses the one which results in the best (leftmost and longest) | |||
| match. This can be spectacularly expensive and may run out of stack | |||
| space, but there really is no better known generic algorithm. Quoting | |||
| Henry Spencer from comp.compilers: | |||
| <URL: http://compilers.iecc.com/comparch/article/93-03-102> | |||
| POSIX.2 REs require longest match, which is really exciting to | |||
| implement since the obsolete ("basic") variant also includes | |||
| \<digit>. I haven't found a better way of tackling this than doing | |||
| a preliminary match using a DFA (or simulation) on a modified RE | |||
| that just replicates subREs for \<digit>, and then doing a | |||
| backtracking match to determine whether the subRE matches were | |||
| right. This can be rather slow, but I console myself with the | |||
| thought that people who use \<digit> deserve very slow execution. | |||
| (Pun unintentional but very appropriate.) | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| /* AIX requires this to be the first thing in the file. */ | |||
| #ifndef __GNUC__ | |||
| # if HAVE_ALLOCA_H | |||
| # include <alloca.h> | |||
| # else | |||
| # ifdef _AIX | |||
| #pragma alloca | |||
| # else | |||
| # ifndef alloca /* predefined by HP cc +Olibcalls */ | |||
| char *alloca (); | |||
| # endif | |||
| # endif | |||
| # endif | |||
| #endif | |||
| #endif /* TRE_USE_ALLOCA */ | |||
| #include <assert.h> | |||
| #include <stdlib.h> | |||
| #include <string.h> | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #ifndef TRE_WCHAR | |||
| #include <ctype.h> | |||
| #endif /* !TRE_WCHAR */ | |||
| #ifdef HAVE_MALLOC_H | |||
| #include <malloc.h> | |||
| #endif /* HAVE_MALLOC_H */ | |||
| #include "tre-internal.h" | |||
| #include "tre-mem.h" | |||
| #include "tre-match-utils.h" | |||
| #include "tre.h" | |||
| #include "xmalloc.h" | |||
| typedef struct { | |||
| int pos; | |||
| const char *str_byte; | |||
| #ifdef TRE_WCHAR | |||
| const wchar_t *str_wide; | |||
| #endif /* TRE_WCHAR */ | |||
| tre_tnfa_transition_t *state; | |||
| int state_id; | |||
| int next_c; | |||
| int *tags; | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_t mbstate; | |||
| #endif /* TRE_MBSTATE */ | |||
| } tre_backtrack_item_t; | |||
| typedef struct tre_backtrack_struct { | |||
| tre_backtrack_item_t item; | |||
| struct tre_backtrack_struct *prev; | |||
| struct tre_backtrack_struct *next; | |||
| } *tre_backtrack_t; | |||
| #ifdef TRE_WCHAR | |||
| #define BT_STACK_WIDE_IN(_str_wide) stack->item.str_wide = (_str_wide) | |||
| #define BT_STACK_WIDE_OUT (str_wide) = stack->item.str_wide | |||
| #else /* !TRE_WCHAR */ | |||
| #define BT_STACK_WIDE_IN(_str_wide) | |||
| #define BT_STACK_WIDE_OUT | |||
| #endif /* !TRE_WCHAR */ | |||
| #ifdef TRE_MBSTATE | |||
| #define BT_STACK_MBSTATE_IN stack->item.mbstate = (mbstate) | |||
| #define BT_STACK_MBSTATE_OUT (mbstate) = stack->item.mbstate | |||
| #else /* !TRE_MBSTATE */ | |||
| #define BT_STACK_MBSTATE_IN | |||
| #define BT_STACK_MBSTATE_OUT | |||
| #endif /* !TRE_MBSTATE */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| #define tre_bt_mem_new tre_mem_newa | |||
| #define tre_bt_mem_alloc tre_mem_alloca | |||
| #define tre_bt_mem_destroy(obj) do { } while (0) | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| #define tre_bt_mem_new tre_mem_new | |||
| #define tre_bt_mem_alloc tre_mem_alloc | |||
| #define tre_bt_mem_destroy tre_mem_destroy | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| #define BT_STACK_PUSH(_pos, _str_byte, _str_wide, _state, _state_id, _next_c, _tags, _mbstate) \ | |||
| do \ | |||
| { \ | |||
| int i; \ | |||
| if (!stack->next) \ | |||
| { \ | |||
| tre_backtrack_t s; \ | |||
| s = tre_bt_mem_alloc(mem, sizeof(*s)); \ | |||
| if (!s) \ | |||
| { \ | |||
| tre_bt_mem_destroy(mem); \ | |||
| if (tags) \ | |||
| xfree(tags); \ | |||
| if (pmatch) \ | |||
| xfree(pmatch); \ | |||
| if (states_seen) \ | |||
| xfree(states_seen); \ | |||
| return REG_ESPACE; \ | |||
| } \ | |||
| s->prev = stack; \ | |||
| s->next = NULL; \ | |||
| s->item.tags = tre_bt_mem_alloc(mem, \ | |||
| sizeof(*tags) * tnfa->num_tags); \ | |||
| if (!s->item.tags) \ | |||
| { \ | |||
| tre_bt_mem_destroy(mem); \ | |||
| if (tags) \ | |||
| xfree(tags); \ | |||
| if (pmatch) \ | |||
| xfree(pmatch); \ | |||
| if (states_seen) \ | |||
| xfree(states_seen); \ | |||
| return REG_ESPACE; \ | |||
| } \ | |||
| stack->next = s; \ | |||
| stack = s; \ | |||
| } \ | |||
| else \ | |||
| stack = stack->next; \ | |||
| stack->item.pos = (_pos); \ | |||
| stack->item.str_byte = (_str_byte); \ | |||
| BT_STACK_WIDE_IN(_str_wide); \ | |||
| stack->item.state = (_state); \ | |||
| stack->item.state_id = (_state_id); \ | |||
| stack->item.next_c = (_next_c); \ | |||
| for (i = 0; i < tnfa->num_tags; i++) \ | |||
| stack->item.tags[i] = (_tags)[i]; \ | |||
| BT_STACK_MBSTATE_IN; \ | |||
| } \ | |||
| while (/*CONSTCOND*/0) | |||
| #define BT_STACK_POP() \ | |||
| do \ | |||
| { \ | |||
| int i; \ | |||
| assert(stack->prev); \ | |||
| pos = stack->item.pos; \ | |||
| if (type == STR_USER) \ | |||
| str_source->rewind(pos + pos_add_next, str_source->context); \ | |||
| str_byte = stack->item.str_byte; \ | |||
| BT_STACK_WIDE_OUT; \ | |||
| state = stack->item.state; \ | |||
| next_c = stack->item.next_c; \ | |||
| for (i = 0; i < tnfa->num_tags; i++) \ | |||
| tags[i] = stack->item.tags[i]; \ | |||
| BT_STACK_MBSTATE_OUT; \ | |||
| stack = stack->prev; \ | |||
| } \ | |||
| while (/*CONSTCOND*/0) | |||
| #undef MIN | |||
| #define MIN(a, b) ((a) <= (b) ? (a) : (b)) | |||
| reg_errcode_t | |||
| tre_tnfa_run_backtrack(const tre_tnfa_t *tnfa, const void *string, | |||
| int len, tre_str_type_t type, int *match_tags, | |||
| int eflags, int *match_end_ofs) | |||
| { | |||
| /* State variables required by GET_NEXT_WCHAR. */ | |||
| tre_char_t prev_c = 0, next_c = 0; | |||
| const char *str_byte = string; | |||
| int pos = 0; | |||
| unsigned int pos_add_next = 1; | |||
| #ifdef TRE_WCHAR | |||
| const wchar_t *str_wide = string; | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_t mbstate; | |||
| #endif /* TRE_MBSTATE */ | |||
| #endif /* TRE_WCHAR */ | |||
| int reg_notbol = eflags & REG_NOTBOL; | |||
| int reg_noteol = eflags & REG_NOTEOL; | |||
| int reg_newline = tnfa->cflags & REG_NEWLINE; | |||
| int str_user_end = 0; | |||
| /* These are used to remember the necessary values of the above | |||
| variables to return to the position where the current search | |||
| started from. */ | |||
| int next_c_start; | |||
| const char *str_byte_start; | |||
| int pos_start = -1; | |||
| #ifdef TRE_WCHAR | |||
| const wchar_t *str_wide_start; | |||
| #endif /* TRE_WCHAR */ | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_t mbstate_start; | |||
| #endif /* TRE_MBSTATE */ | |||
| /* End offset of best match so far, or -1 if no match found yet. */ | |||
| int match_eo = -1; | |||
| /* Tag arrays. */ | |||
| int *next_tags, *tags = NULL; | |||
| /* Current TNFA state. */ | |||
| tre_tnfa_transition_t *state; | |||
| int *states_seen = NULL; | |||
| /* Memory allocator to for allocating the backtracking stack. */ | |||
| tre_mem_t mem = tre_bt_mem_new(); | |||
| /* The backtracking stack. */ | |||
| tre_backtrack_t stack; | |||
| tre_tnfa_transition_t *trans_i; | |||
| regmatch_t *pmatch = NULL; | |||
| int ret; | |||
| #ifdef TRE_MBSTATE | |||
| memset(&mbstate, '\0', sizeof(mbstate)); | |||
| #endif /* TRE_MBSTATE */ | |||
| if (!mem) | |||
| return REG_ESPACE; | |||
| stack = tre_bt_mem_alloc(mem, sizeof(*stack)); | |||
| if (!stack) | |||
| { | |||
| ret = REG_ESPACE; | |||
| goto error_exit; | |||
| } | |||
| stack->prev = NULL; | |||
| stack->next = NULL; | |||
| DPRINT(("tnfa_execute_backtrack, input type %d\n", type)); | |||
| DPRINT(("len = %d\n", len)); | |||
| #ifdef TRE_USE_ALLOCA | |||
| tags = alloca(sizeof(*tags) * tnfa->num_tags); | |||
| pmatch = alloca(sizeof(*pmatch) * tnfa->num_submatches); | |||
| states_seen = alloca(sizeof(*states_seen) * tnfa->num_states); | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| if (tnfa->num_tags) | |||
| { | |||
| tags = xmalloc(sizeof(*tags) * tnfa->num_tags); | |||
| if (!tags) | |||
| { | |||
| ret = REG_ESPACE; | |||
| goto error_exit; | |||
| } | |||
| } | |||
| if (tnfa->num_submatches) | |||
| { | |||
| pmatch = xmalloc(sizeof(*pmatch) * tnfa->num_submatches); | |||
| if (!pmatch) | |||
| { | |||
| ret = REG_ESPACE; | |||
| goto error_exit; | |||
| } | |||
| } | |||
| if (tnfa->num_states) | |||
| { | |||
| states_seen = xmalloc(sizeof(*states_seen) * tnfa->num_states); | |||
| if (!states_seen) | |||
| { | |||
| ret = REG_ESPACE; | |||
| goto error_exit; | |||
| } | |||
| } | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| retry: | |||
| { | |||
| int i; | |||
| for (i = 0; i < tnfa->num_tags; i++) | |||
| { | |||
| tags[i] = -1; | |||
| if (match_tags) | |||
| match_tags[i] = -1; | |||
| } | |||
| for (i = 0; i < tnfa->num_states; i++) | |||
| states_seen[i] = 0; | |||
| } | |||
| state = NULL; | |||
| pos = pos_start; | |||
| if (type == STR_USER) | |||
| str_source->rewind(pos + pos_add_next, str_source->context); | |||
| GET_NEXT_WCHAR(); | |||
| pos_start = pos; | |||
| next_c_start = next_c; | |||
| str_byte_start = str_byte; | |||
| #ifdef TRE_WCHAR | |||
| str_wide_start = str_wide; | |||
| #endif /* TRE_WCHAR */ | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_start = mbstate; | |||
| #endif /* TRE_MBSTATE */ | |||
| /* Handle initial states. */ | |||
| next_tags = NULL; | |||
| for (trans_i = tnfa->initial; trans_i->state; trans_i++) | |||
| { | |||
| DPRINT(("> init %p, prev_c %lc\n", trans_i->state, (tre_cint_t)prev_c)); | |||
| if (trans_i->assertions && CHECK_ASSERTIONS(trans_i->assertions)) | |||
| { | |||
| DPRINT(("assert failed\n")); | |||
| continue; | |||
| } | |||
| if (state == NULL) | |||
| { | |||
| /* Start from this state. */ | |||
| state = trans_i->state; | |||
| next_tags = trans_i->tags; | |||
| } | |||
| else | |||
| { | |||
| /* Backtrack to this state. */ | |||
| DPRINT(("saving state %d for backtracking\n", trans_i->state_id)); | |||
| BT_STACK_PUSH(pos, str_byte, str_wide, trans_i->state, | |||
| trans_i->state_id, next_c, tags, mbstate); | |||
| { | |||
| int *tmp = trans_i->tags; | |||
| if (tmp) | |||
| while (*tmp >= 0) | |||
| stack->item.tags[*tmp++] = pos; | |||
| } | |||
| } | |||
| } | |||
| if (next_tags) | |||
| for (; *next_tags >= 0; next_tags++) | |||
| tags[*next_tags] = pos; | |||
| DPRINT(("entering match loop, pos %d, str_byte %p\n", pos, str_byte)); | |||
| DPRINT(("pos:chr/code | state and tags\n")); | |||
| DPRINT(("-------------+------------------------------------------------\n")); | |||
| if (state == NULL) | |||
| goto backtrack; | |||
| while (/*CONSTCOND*/1) | |||
| { | |||
| tre_tnfa_transition_t *next_state; | |||
| int empty_br_match; | |||
| DPRINT(("start loop\n")); | |||
| if (state == tnfa->final) | |||
| { | |||
| DPRINT((" match found, %d %d\n", match_eo, pos)); | |||
| if (match_eo < pos | |||
| || (match_eo == pos | |||
| && match_tags | |||
| && tre_tag_order(tnfa->num_tags, tnfa->tag_directions, | |||
| tags, match_tags))) | |||
| { | |||
| int i; | |||
| /* This match wins the previous match. */ | |||
| DPRINT((" win previous\n")); | |||
| match_eo = pos; | |||
| if (match_tags) | |||
| for (i = 0; i < tnfa->num_tags; i++) | |||
| match_tags[i] = tags[i]; | |||
| } | |||
| /* Our TNFAs never have transitions leaving from the final state, | |||
| so we jump right to backtracking. */ | |||
| goto backtrack; | |||
| } | |||
| #ifdef TRE_DEBUG | |||
| DPRINT(("%3d:%2lc/%05d | %p ", pos, (tre_cint_t)next_c, (int)next_c, | |||
| state)); | |||
| { | |||
| int i; | |||
| for (i = 0; i < tnfa->num_tags; i++) | |||
| DPRINT(("%d%s", tags[i], i < tnfa->num_tags - 1 ? ", " : "")); | |||
| DPRINT(("\n")); | |||
| } | |||
| #endif /* TRE_DEBUG */ | |||
| /* Go to the next character in the input string. */ | |||
| empty_br_match = 0; | |||
| trans_i = state; | |||
| if (trans_i->state && trans_i->assertions & ASSERT_BACKREF) | |||
| { | |||
| /* This is a back reference state. All transitions leaving from | |||
| this state have the same back reference "assertion". Instead | |||
| of reading the next character, we match the back reference. */ | |||
| int so, eo, bt = trans_i->u.backref; | |||
| int bt_len; | |||
| int result; | |||
| DPRINT((" should match back reference %d\n", bt)); | |||
| /* Get the substring we need to match against. Remember to | |||
| turn off REG_NOSUB temporarily. */ | |||
| tre_fill_pmatch(bt + 1, pmatch, tnfa->cflags & /*LINTED*/!REG_NOSUB, | |||
| tnfa, tags, pos); | |||
| so = pmatch[bt].rm_so; | |||
| eo = pmatch[bt].rm_eo; | |||
| bt_len = eo - so; | |||
| #ifdef TRE_DEBUG | |||
| { | |||
| int slen; | |||
| if (len < 0) | |||
| slen = bt_len; | |||
| else | |||
| slen = MIN(bt_len, len - pos); | |||
| if (type == STR_BYTE) | |||
| { | |||
| DPRINT((" substring (len %d) is [%d, %d[: '%.*s'\n", | |||
| bt_len, so, eo, bt_len, (char*)string + so)); | |||
| DPRINT((" current string is '%.*s'\n", slen, str_byte - 1)); | |||
| } | |||
| #ifdef TRE_WCHAR | |||
| else if (type == STR_WIDE) | |||
| { | |||
| DPRINT((" substring (len %d) is [%d, %d[: '%.*" STRF "'\n", | |||
| bt_len, so, eo, bt_len, (wchar_t*)string + so)); | |||
| DPRINT((" current string is '%.*" STRF "'\n", | |||
| slen, str_wide - 1)); | |||
| } | |||
| #endif /* TRE_WCHAR */ | |||
| } | |||
| #endif | |||
| if (len < 0) | |||
| { | |||
| if (type == STR_USER) | |||
| result = str_source->compare((unsigned)so, (unsigned)pos, | |||
| (unsigned)bt_len, | |||
| str_source->context); | |||
| #ifdef TRE_WCHAR | |||
| else if (type == STR_WIDE) | |||
| result = wcsncmp((const wchar_t*)string + so, str_wide - 1, | |||
| (size_t)bt_len); | |||
| #endif /* TRE_WCHAR */ | |||
| else | |||
| result = strncmp((const char*)string + so, str_byte - 1, | |||
| (size_t)bt_len); | |||
| } | |||
| else if (len - pos < bt_len) | |||
| result = 1; | |||
| #ifdef TRE_WCHAR | |||
| else if (type == STR_WIDE) | |||
| result = wmemcmp((const wchar_t*)string + so, str_wide - 1, | |||
| (size_t)bt_len); | |||
| #endif /* TRE_WCHAR */ | |||
| else | |||
| result = memcmp((const char*)string + so, str_byte - 1, | |||
| (size_t)bt_len); | |||
| if (result == 0) | |||
| { | |||
| /* Back reference matched. Check for infinite loop. */ | |||
| if (bt_len == 0) | |||
| empty_br_match = 1; | |||
| if (empty_br_match && states_seen[trans_i->state_id]) | |||
| { | |||
| DPRINT((" avoid loop\n")); | |||
| goto backtrack; | |||
| } | |||
| states_seen[trans_i->state_id] = empty_br_match; | |||
| /* Advance in input string and resync `prev_c', `next_c' | |||
| and pos. */ | |||
| DPRINT((" back reference matched\n")); | |||
| str_byte += bt_len - 1; | |||
| #ifdef TRE_WCHAR | |||
| str_wide += bt_len - 1; | |||
| #endif /* TRE_WCHAR */ | |||
| pos += bt_len - 1; | |||
| GET_NEXT_WCHAR(); | |||
| DPRINT((" pos now %d\n", pos)); | |||
| } | |||
| else | |||
| { | |||
| DPRINT((" back reference did not match\n")); | |||
| goto backtrack; | |||
| } | |||
| } | |||
| else | |||
| { | |||
| /* Check for end of string. */ | |||
| if (len < 0) | |||
| { | |||
| if (type == STR_USER) | |||
| { | |||
| if (str_user_end) | |||
| goto backtrack; | |||
| } | |||
| else if (next_c == L'\0') | |||
| goto backtrack; | |||
| } | |||
| else | |||
| { | |||
| if (pos >= len) | |||
| goto backtrack; | |||
| } | |||
| /* Read the next character. */ | |||
| GET_NEXT_WCHAR(); | |||
| } | |||
| next_state = NULL; | |||
| for (trans_i = state; trans_i->state; trans_i++) | |||
| { | |||
| DPRINT((" transition %d-%d (%c-%c) %d to %d\n", | |||
| trans_i->code_min, trans_i->code_max, | |||
| trans_i->code_min, trans_i->code_max, | |||
| trans_i->assertions, trans_i->state_id)); | |||
| if (trans_i->code_min <= (tre_cint_t)prev_c | |||
| && trans_i->code_max >= (tre_cint_t)prev_c) | |||
| { | |||
| if (trans_i->assertions | |||
| && (CHECK_ASSERTIONS(trans_i->assertions) | |||
| || CHECK_CHAR_CLASSES(trans_i, tnfa, eflags))) | |||
| { | |||
| DPRINT((" assertion failed\n")); | |||
| continue; | |||
| } | |||
| if (next_state == NULL) | |||
| { | |||
| /* First matching transition. */ | |||
| DPRINT((" Next state is %d\n", trans_i->state_id)); | |||
| next_state = trans_i->state; | |||
| next_tags = trans_i->tags; | |||
| } | |||
| else | |||
| { | |||
| /* Second matching transition. We may need to backtrack here | |||
| to take this transition instead of the first one, so we | |||
| push this transition in the backtracking stack so we can | |||
| jump back here if needed. */ | |||
| DPRINT((" saving state %d for backtracking\n", | |||
| trans_i->state_id)); | |||
| BT_STACK_PUSH(pos, str_byte, str_wide, trans_i->state, | |||
| trans_i->state_id, next_c, tags, mbstate); | |||
| { | |||
| int *tmp; | |||
| for (tmp = trans_i->tags; tmp && *tmp >= 0; tmp++) | |||
| stack->item.tags[*tmp] = pos; | |||
| } | |||
| #if 0 /* XXX - it's important not to look at all transitions here to keep | |||
| the stack small! */ | |||
| break; | |||
| #endif | |||
| } | |||
| } | |||
| } | |||
| if (next_state != NULL) | |||
| { | |||
| /* Matching transitions were found. Take the first one. */ | |||
| state = next_state; | |||
| /* Update the tag values. */ | |||
| if (next_tags) | |||
| while (*next_tags >= 0) | |||
| tags[*next_tags++] = pos; | |||
| } | |||
| else | |||
| { | |||
| backtrack: | |||
| /* A matching transition was not found. Try to backtrack. */ | |||
| if (stack->prev) | |||
| { | |||
| DPRINT((" backtracking\n")); | |||
| if (stack->item.state->assertions && ASSERT_BACKREF) | |||
| { | |||
| DPRINT((" states_seen[%d] = 0\n", | |||
| stack->item.state_id)); | |||
| states_seen[stack->item.state_id] = 0; | |||
| } | |||
| BT_STACK_POP(); | |||
| } | |||
| else if (match_eo < 0) | |||
| { | |||
| /* Try starting from a later position in the input string. */ | |||
| /* Check for end of string. */ | |||
| if (len < 0) | |||
| { | |||
| if (next_c == L'\0') | |||
| { | |||
| DPRINT(("end of string.\n")); | |||
| break; | |||
| } | |||
| } | |||
| else | |||
| { | |||
| if (pos >= len) | |||
| { | |||
| DPRINT(("end of string.\n")); | |||
| break; | |||
| } | |||
| } | |||
| DPRINT(("restarting from next start position\n")); | |||
| next_c = next_c_start; | |||
| #ifdef TRE_MBSTATE | |||
| mbstate = mbstate_start; | |||
| #endif /* TRE_MBSTATE */ | |||
| str_byte = str_byte_start; | |||
| #ifdef TRE_WCHAR | |||
| str_wide = str_wide_start; | |||
| #endif /* TRE_WCHAR */ | |||
| goto retry; | |||
| } | |||
| else | |||
| { | |||
| DPRINT(("finished\n")); | |||
| break; | |||
| } | |||
| } | |||
| } | |||
| ret = match_eo >= 0 ? REG_OK : REG_NOMATCH; | |||
| *match_end_ofs = match_eo; | |||
| error_exit: | |||
| tre_bt_mem_destroy(mem); | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (tags) | |||
| xfree(tags); | |||
| if (pmatch) | |||
| xfree(pmatch); | |||
| if (states_seen) | |||
| xfree(states_seen); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| return ret; | |||
| } | |||
| @@ -0,0 +1,501 @@ | |||
| /* | |||
| tre-match-parallel.c - TRE parallel regex matching engine | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| /* | |||
| This algorithm searches for matches basically by reading characters | |||
| in the searched string one by one, starting at the beginning. All | |||
| matching paths in the TNFA are traversed in parallel. When two or | |||
| more paths reach the same state, exactly one is chosen according to | |||
| tag ordering rules; if returning submatches is not required it does | |||
| not matter which path is chosen. | |||
| The worst case time required for finding the leftmost and longest | |||
| match, or determining that there is no match, is always linearly | |||
| dependent on the length of the text being searched. | |||
| This algorithm cannot handle TNFAs with back referencing nodes. | |||
| See `tre-match-backtrack.c'. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| /* AIX requires this to be the first thing in the file. */ | |||
| #ifndef __GNUC__ | |||
| # if HAVE_ALLOCA_H | |||
| # include <alloca.h> | |||
| # else | |||
| # ifdef _AIX | |||
| #pragma alloca | |||
| # else | |||
| # ifndef alloca /* predefined by HP cc +Olibcalls */ | |||
| char *alloca (); | |||
| # endif | |||
| # endif | |||
| # endif | |||
| #endif | |||
| #endif /* TRE_USE_ALLOCA */ | |||
| #include <assert.h> | |||
| #include <stdlib.h> | |||
| #include <string.h> | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| #ifdef HAVE_WCTYPE_H | |||
| #include <wctype.h> | |||
| #endif /* HAVE_WCTYPE_H */ | |||
| #ifndef TRE_WCHAR | |||
| #include <ctype.h> | |||
| #endif /* !TRE_WCHAR */ | |||
| #ifdef HAVE_MALLOC_H | |||
| #include <malloc.h> | |||
| #endif /* HAVE_MALLOC_H */ | |||
| #include "tre-internal.h" | |||
| #include "tre-match-utils.h" | |||
| #include "tre.h" | |||
| #include "xmalloc.h" | |||
| typedef struct { | |||
| tre_tnfa_transition_t *state; | |||
| int *tags; | |||
| } tre_tnfa_reach_t; | |||
| typedef struct { | |||
| int pos; | |||
| int **tags; | |||
| } tre_reach_pos_t; | |||
| #ifdef TRE_DEBUG | |||
| static void | |||
| tre_print_reach(const tre_tnfa_t *tnfa, tre_tnfa_reach_t *reach, int num_tags) | |||
| { | |||
| int i; | |||
| while (reach->state != NULL) | |||
| { | |||
| DPRINT((" %p", (void *)reach->state)); | |||
| if (num_tags > 0) | |||
| { | |||
| DPRINT(("/")); | |||
| for (i = 0; i < num_tags; i++) | |||
| { | |||
| DPRINT(("%d:%d", i, reach->tags[i])); | |||
| if (i < (num_tags-1)) | |||
| DPRINT((",")); | |||
| } | |||
| } | |||
| reach++; | |||
| } | |||
| DPRINT(("\n")); | |||
| } | |||
| #endif /* TRE_DEBUG */ | |||
| reg_errcode_t | |||
| tre_tnfa_run_parallel(const tre_tnfa_t *tnfa, const void *string, int len, | |||
| tre_str_type_t type, int *match_tags, int eflags, | |||
| int *match_end_ofs) | |||
| { | |||
| /* State variables required by GET_NEXT_WCHAR. */ | |||
| tre_char_t prev_c = 0, next_c = 0; | |||
| const char *str_byte = string; | |||
| int pos = -1; | |||
| unsigned int pos_add_next = 1; | |||
| #ifdef TRE_WCHAR | |||
| const wchar_t *str_wide = string; | |||
| #ifdef TRE_MBSTATE | |||
| mbstate_t mbstate; | |||
| #endif /* TRE_MBSTATE */ | |||
| #endif /* TRE_WCHAR */ | |||
| int reg_notbol = eflags & REG_NOTBOL; | |||
| int reg_noteol = eflags & REG_NOTEOL; | |||
| int reg_newline = tnfa->cflags & REG_NEWLINE; | |||
| int str_user_end = 0; | |||
| char *buf; | |||
| tre_tnfa_transition_t *trans_i; | |||
| tre_tnfa_reach_t *reach, *reach_next, *reach_i, *reach_next_i; | |||
| tre_reach_pos_t *reach_pos; | |||
| int *tag_i; | |||
| int num_tags, i; | |||
| int match_eo = -1; /* end offset of match (-1 if no match found yet) */ | |||
| int new_match = 0; | |||
| int *tmp_tags = NULL; | |||
| int *tmp_iptr; | |||
| #ifdef TRE_MBSTATE | |||
| memset(&mbstate, '\0', sizeof(mbstate)); | |||
| #endif /* TRE_MBSTATE */ | |||
| DPRINT(("tre_tnfa_run_parallel, input type %d\n", type)); | |||
| if (!match_tags) | |||
| num_tags = 0; | |||
| else | |||
| num_tags = tnfa->num_tags; | |||
| /* Allocate memory for temporary data required for matching. This needs to | |||
| be done for every matching operation to be thread safe. This allocates | |||
| everything in a single large block from the stack frame using alloca() | |||
| or with malloc() if alloca is unavailable. */ | |||
| { | |||
| int tbytes, rbytes, pbytes, xbytes, total_bytes; | |||
| char *tmp_buf; | |||
| /* Compute the length of the block we need. */ | |||
| tbytes = sizeof(*tmp_tags) * num_tags; | |||
| rbytes = sizeof(*reach_next) * (tnfa->num_states + 1); | |||
| pbytes = sizeof(*reach_pos) * tnfa->num_states; | |||
| xbytes = sizeof(int) * num_tags; | |||
| total_bytes = | |||
| (sizeof(long) - 1) * 4 /* for alignment paddings */ | |||
| + (rbytes + xbytes * tnfa->num_states) * 2 + tbytes + pbytes; | |||
| /* Allocate the memory. */ | |||
| #ifdef TRE_USE_ALLOCA | |||
| buf = alloca(total_bytes); | |||
| #else /* !TRE_USE_ALLOCA */ | |||
| buf = xmalloc((unsigned)total_bytes); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| if (buf == NULL) | |||
| return REG_ESPACE; | |||
| memset(buf, 0, (size_t)total_bytes); | |||
| /* Get the various pointers within tmp_buf (properly aligned). */ | |||
| tmp_tags = (void *)buf; | |||
| tmp_buf = buf + tbytes; | |||
| tmp_buf += ALIGN(tmp_buf, long); | |||
| reach_next = (void *)tmp_buf; | |||
| tmp_buf += rbytes; | |||
| tmp_buf += ALIGN(tmp_buf, long); | |||
| reach = (void *)tmp_buf; | |||
| tmp_buf += rbytes; | |||
| tmp_buf += ALIGN(tmp_buf, long); | |||
| reach_pos = (void *)tmp_buf; | |||
| tmp_buf += pbytes; | |||
| tmp_buf += ALIGN(tmp_buf, long); | |||
| for (i = 0; i < tnfa->num_states; i++) | |||
| { | |||
| reach[i].tags = (void *)tmp_buf; | |||
| tmp_buf += xbytes; | |||
| reach_next[i].tags = (void *)tmp_buf; | |||
| tmp_buf += xbytes; | |||
| } | |||
| } | |||
| for (i = 0; i < tnfa->num_states; i++) | |||
| reach_pos[i].pos = -1; | |||
| /* If only one character can start a match, find it first. */ | |||
| if (tnfa->first_char >= 0 && type == STR_BYTE && str_byte) | |||
| { | |||
| const char *orig_str = str_byte; | |||
| int first = tnfa->first_char; | |||
| if (len >= 0) | |||
| str_byte = memchr(orig_str, first, (size_t)len); | |||
| else | |||
| str_byte = strchr(orig_str, first); | |||
| if (str_byte == NULL) | |||
| { | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (buf) | |||
| xfree(buf); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| return REG_NOMATCH; | |||
| } | |||
| DPRINT(("skipped %lu chars\n", (unsigned long)(str_byte - orig_str))); | |||
| if (str_byte >= orig_str + 1) | |||
| prev_c = (unsigned char)*(str_byte - 1); | |||
| next_c = (unsigned char)*str_byte; | |||
| pos = str_byte - orig_str; | |||
| if (len < 0 || pos < len) | |||
| str_byte++; | |||
| } | |||
| else | |||
| { | |||
| GET_NEXT_WCHAR(); | |||
| pos = 0; | |||
| } | |||
| #if 0 | |||
| /* Skip over characters that cannot possibly be the first character | |||
| of a match. */ | |||
| if (tnfa->firstpos_chars != NULL) | |||
| { | |||
| char *chars = tnfa->firstpos_chars; | |||
| if (len < 0) | |||
| { | |||
| const char *orig_str = str_byte; | |||
| /* XXX - use strpbrk() and wcspbrk() because they might be | |||
| optimized for the target architecture. Try also strcspn() | |||
| and wcscspn() and compare the speeds. */ | |||
| while (next_c != L'\0' && !chars[next_c]) | |||
| { | |||
| next_c = *str_byte++; | |||
| } | |||
| prev_c = *(str_byte - 2); | |||
| pos += str_byte - orig_str; | |||
| DPRINT(("skipped %d chars\n", str_byte - orig_str)); | |||
| } | |||
| else | |||
| { | |||
| while (pos <= len && !chars[next_c]) | |||
| { | |||
| prev_c = next_c; | |||
| next_c = (unsigned char)(*str_byte++); | |||
| pos++; | |||
| } | |||
| } | |||
| } | |||
| #endif | |||
| DPRINT(("length: %d\n", len)); | |||
| DPRINT(("pos:chr/code | states and tags\n")); | |||
| DPRINT(("-------------+------------------------------------------------\n")); | |||
| reach_next_i = reach_next; | |||
| while (/*CONSTCOND*/1) | |||
| { | |||
| /* If no match found yet, add the initial states to `reach_next'. */ | |||
| if (match_eo < 0) | |||
| { | |||
| DPRINT((" init >")); | |||
| trans_i = tnfa->initial; | |||
| while (trans_i->state != NULL) | |||
| { | |||
| if (reach_pos[trans_i->state_id].pos < pos) | |||
| { | |||
| if (trans_i->assertions | |||
| && CHECK_ASSERTIONS(trans_i->assertions)) | |||
| { | |||
| DPRINT(("assertion failed\n")); | |||
| trans_i++; | |||
| continue; | |||
| } | |||
| DPRINT((" %p", (void *)trans_i->state)); | |||
| reach_next_i->state = trans_i->state; | |||
| for (i = 0; i < num_tags; i++) | |||
| reach_next_i->tags[i] = -1; | |||
| tag_i = trans_i->tags; | |||
| if (tag_i) | |||
| while (*tag_i >= 0) | |||
| { | |||
| if (*tag_i < num_tags) | |||
| reach_next_i->tags[*tag_i] = pos; | |||
| tag_i++; | |||
| } | |||
| if (reach_next_i->state == tnfa->final) | |||
| { | |||
| DPRINT((" found empty match\n")); | |||
| match_eo = pos; | |||
| new_match = 1; | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = reach_next_i->tags[i]; | |||
| } | |||
| reach_pos[trans_i->state_id].pos = pos; | |||
| reach_pos[trans_i->state_id].tags = &reach_next_i->tags; | |||
| reach_next_i++; | |||
| } | |||
| trans_i++; | |||
| } | |||
| DPRINT(("\n")); | |||
| reach_next_i->state = NULL; | |||
| } | |||
| else | |||
| { | |||
| if (num_tags == 0 || reach_next_i == reach_next) | |||
| /* We have found a match. */ | |||
| break; | |||
| } | |||
| /* Check for end of string. */ | |||
| if (len < 0) | |||
| { | |||
| if (type == STR_USER) | |||
| { | |||
| if (str_user_end) | |||
| break; | |||
| } | |||
| else if (next_c == L'\0') | |||
| break; | |||
| } | |||
| else | |||
| { | |||
| if (pos >= len) | |||
| break; | |||
| } | |||
| GET_NEXT_WCHAR(); | |||
| #ifdef TRE_DEBUG | |||
| DPRINT(("%3d:%2lc/%05d |", pos - 1, (tre_cint_t)prev_c, (int)prev_c)); | |||
| tre_print_reach(tnfa, reach_next, num_tags); | |||
| DPRINT(("%3d:%2lc/%05d |", pos, (tre_cint_t)next_c, (int)next_c)); | |||
| tre_print_reach(tnfa, reach_next, num_tags); | |||
| #endif /* TRE_DEBUG */ | |||
| /* Swap `reach' and `reach_next'. */ | |||
| reach_i = reach; | |||
| reach = reach_next; | |||
| reach_next = reach_i; | |||
| /* For each state in `reach', weed out states that don't fulfill the | |||
| minimal matching conditions. */ | |||
| if (tnfa->num_minimals && new_match) | |||
| { | |||
| new_match = 0; | |||
| reach_next_i = reach_next; | |||
| for (reach_i = reach; reach_i->state; reach_i++) | |||
| { | |||
| int skip = 0; | |||
| for (i = 0; tnfa->minimal_tags[i] >= 0; i += 2) | |||
| { | |||
| int end = tnfa->minimal_tags[i]; | |||
| int start = tnfa->minimal_tags[i + 1]; | |||
| DPRINT((" Minimal start %d, end %d\n", start, end)); | |||
| if (end >= num_tags) | |||
| { | |||
| DPRINT((" Throwing %p out.\n", reach_i->state)); | |||
| skip = 1; | |||
| break; | |||
| } | |||
| else if (reach_i->tags[start] == match_tags[start] | |||
| && reach_i->tags[end] < match_tags[end]) | |||
| { | |||
| DPRINT((" Throwing %p out because t%d < %d\n", | |||
| reach_i->state, end, match_tags[end])); | |||
| skip = 1; | |||
| break; | |||
| } | |||
| } | |||
| if (!skip) | |||
| { | |||
| reach_next_i->state = reach_i->state; | |||
| tmp_iptr = reach_next_i->tags; | |||
| reach_next_i->tags = reach_i->tags; | |||
| reach_i->tags = tmp_iptr; | |||
| reach_next_i++; | |||
| } | |||
| } | |||
| reach_next_i->state = NULL; | |||
| /* Swap `reach' and `reach_next'. */ | |||
| reach_i = reach; | |||
| reach = reach_next; | |||
| reach_next = reach_i; | |||
| } | |||
| /* For each state in `reach' see if there is a transition leaving with | |||
| the current input symbol to a state not yet in `reach_next', and | |||
| add the destination states to `reach_next'. */ | |||
| reach_next_i = reach_next; | |||
| for (reach_i = reach; reach_i->state; reach_i++) | |||
| { | |||
| for (trans_i = reach_i->state; trans_i->state; trans_i++) | |||
| { | |||
| /* Does this transition match the input symbol? */ | |||
| if (trans_i->code_min <= (tre_cint_t)prev_c && | |||
| trans_i->code_max >= (tre_cint_t)prev_c) | |||
| { | |||
| if (trans_i->assertions | |||
| && (CHECK_ASSERTIONS(trans_i->assertions) | |||
| || CHECK_CHAR_CLASSES(trans_i, tnfa, eflags))) | |||
| { | |||
| DPRINT(("assertion failed\n")); | |||
| continue; | |||
| } | |||
| /* Compute the tags after this transition. */ | |||
| for (i = 0; i < num_tags; i++) | |||
| tmp_tags[i] = reach_i->tags[i]; | |||
| tag_i = trans_i->tags; | |||
| if (tag_i != NULL) | |||
| while (*tag_i >= 0) | |||
| { | |||
| if (*tag_i < num_tags) | |||
| tmp_tags[*tag_i] = pos; | |||
| tag_i++; | |||
| } | |||
| if (reach_pos[trans_i->state_id].pos < pos) | |||
| { | |||
| /* Found an unvisited node. */ | |||
| reach_next_i->state = trans_i->state; | |||
| tmp_iptr = reach_next_i->tags; | |||
| reach_next_i->tags = tmp_tags; | |||
| tmp_tags = tmp_iptr; | |||
| reach_pos[trans_i->state_id].pos = pos; | |||
| reach_pos[trans_i->state_id].tags = &reach_next_i->tags; | |||
| if (reach_next_i->state == tnfa->final | |||
| && (match_eo == -1 | |||
| || (num_tags > 0 | |||
| && reach_next_i->tags[0] <= match_tags[0]))) | |||
| { | |||
| DPRINT((" found match %p\n", trans_i->state)); | |||
| match_eo = pos; | |||
| new_match = 1; | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = reach_next_i->tags[i]; | |||
| } | |||
| reach_next_i++; | |||
| } | |||
| else | |||
| { | |||
| assert(reach_pos[trans_i->state_id].pos == pos); | |||
| /* Another path has also reached this state. We choose | |||
| the winner by examining the tag values for both | |||
| paths. */ | |||
| if (tre_tag_order(num_tags, tnfa->tag_directions, | |||
| tmp_tags, | |||
| *reach_pos[trans_i->state_id].tags)) | |||
| { | |||
| /* The new path wins. */ | |||
| tmp_iptr = *reach_pos[trans_i->state_id].tags; | |||
| *reach_pos[trans_i->state_id].tags = tmp_tags; | |||
| if (trans_i->state == tnfa->final) | |||
| { | |||
| DPRINT((" found better match\n")); | |||
| match_eo = pos; | |||
| new_match = 1; | |||
| for (i = 0; i < num_tags; i++) | |||
| match_tags[i] = tmp_tags[i]; | |||
| } | |||
| tmp_tags = tmp_iptr; | |||
| } | |||
| } | |||
| } | |||
| } | |||
| } | |||
| reach_next_i->state = NULL; | |||
| } | |||
| DPRINT(("match end offset = %d\n", match_eo)); | |||
| #ifndef TRE_USE_ALLOCA | |||
| if (buf) | |||
| xfree(buf); | |||
| #endif /* !TRE_USE_ALLOCA */ | |||
| *match_end_ofs = match_eo; | |||
| return match_eo >= 0 ? REG_OK : REG_NOMATCH; | |||
| } | |||
| /* EOF */ | |||
| @@ -0,0 +1,215 @@ | |||
| /* | |||
| tre-match-utils.h - TRE matcher helper definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #define str_source ((const tre_str_source*)string) | |||
| #ifdef TRE_WCHAR | |||
| #ifdef TRE_MULTIBYTE | |||
| /* Wide character and multibyte support. */ | |||
| #define GET_NEXT_WCHAR() \ | |||
| do { \ | |||
| prev_c = next_c; \ | |||
| if (type == STR_BYTE) \ | |||
| { \ | |||
| pos++; \ | |||
| if (len >= 0 && pos >= len) \ | |||
| next_c = '\0'; \ | |||
| else \ | |||
| next_c = (unsigned char)(*str_byte++); \ | |||
| } \ | |||
| else if (type == STR_WIDE) \ | |||
| { \ | |||
| pos++; \ | |||
| if (len >= 0 && pos >= len) \ | |||
| next_c = L'\0'; \ | |||
| else \ | |||
| next_c = *str_wide++; \ | |||
| } \ | |||
| else if (type == STR_MBS) \ | |||
| { \ | |||
| pos += pos_add_next; \ | |||
| if (str_byte == NULL) \ | |||
| next_c = L'\0'; \ | |||
| else \ | |||
| { \ | |||
| size_t w; \ | |||
| int max; \ | |||
| if (len >= 0) \ | |||
| max = len - pos; \ | |||
| else \ | |||
| max = 32; \ | |||
| if (max <= 0) \ | |||
| { \ | |||
| next_c = L'\0'; \ | |||
| pos_add_next = 1; \ | |||
| } \ | |||
| else \ | |||
| { \ | |||
| w = tre_mbrtowc(&next_c, str_byte, (size_t)max, &mbstate); \ | |||
| if (w == (size_t)-1 || w == (size_t)-2) \ | |||
| return REG_NOMATCH; \ | |||
| if (w == 0 && len >= 0) \ | |||
| { \ | |||
| pos_add_next = 1; \ | |||
| next_c = 0; \ | |||
| str_byte++; \ | |||
| } \ | |||
| else \ | |||
| { \ | |||
| pos_add_next = w; \ | |||
| str_byte += w; \ | |||
| } \ | |||
| } \ | |||
| } \ | |||
| } \ | |||
| else if (type == STR_USER) \ | |||
| { \ | |||
| pos += pos_add_next; \ | |||
| str_user_end = str_source->get_next_char(&next_c, &pos_add_next, \ | |||
| str_source->context); \ | |||
| } \ | |||
| } while(/*CONSTCOND*/0) | |||
| #else /* !TRE_MULTIBYTE */ | |||
| /* Wide character support, no multibyte support. */ | |||
| #define GET_NEXT_WCHAR() \ | |||
| do { \ | |||
| prev_c = next_c; \ | |||
| if (type == STR_BYTE) \ | |||
| { \ | |||
| pos++; \ | |||
| if (len >= 0 && pos >= len) \ | |||
| next_c = '\0'; \ | |||
| else \ | |||
| next_c = (unsigned char)(*str_byte++); \ | |||
| } \ | |||
| else if (type == STR_WIDE) \ | |||
| { \ | |||
| pos++; \ | |||
| if (len >= 0 && pos >= len) \ | |||
| next_c = L'\0'; \ | |||
| else \ | |||
| next_c = *str_wide++; \ | |||
| } \ | |||
| else if (type == STR_USER) \ | |||
| { \ | |||
| pos += pos_add_next; \ | |||
| str_user_end = str_source->get_next_char(&next_c, &pos_add_next, \ | |||
| str_source->context); \ | |||
| } \ | |||
| } while(/*CONSTCOND*/0) | |||
| #endif /* !TRE_MULTIBYTE */ | |||
| #else /* !TRE_WCHAR */ | |||
| /* No wide character or multibyte support. */ | |||
| #define GET_NEXT_WCHAR() \ | |||
| do { \ | |||
| prev_c = next_c; \ | |||
| if (type == STR_BYTE) \ | |||
| { \ | |||
| pos++; \ | |||
| if (len >= 0 && pos >= len) \ | |||
| next_c = '\0'; \ | |||
| else \ | |||
| next_c = (unsigned char)(*str_byte++); \ | |||
| } \ | |||
| else if (type == STR_USER) \ | |||
| { \ | |||
| pos += pos_add_next; \ | |||
| str_user_end = str_source->get_next_char(&next_c, &pos_add_next, \ | |||
| str_source->context); \ | |||
| } \ | |||
| } while(/*CONSTCOND*/0) | |||
| #endif /* !TRE_WCHAR */ | |||
| #define IS_WORD_CHAR(c) ((c) == L'_' || tre_isalnum(c)) | |||
| #define CHECK_ASSERTIONS(assertions) \ | |||
| (((assertions & ASSERT_AT_BOL) \ | |||
| && (pos > 0 || reg_notbol) \ | |||
| && (prev_c != L'\n' || !reg_newline)) \ | |||
| || ((assertions & ASSERT_AT_EOL) \ | |||
| && (next_c != L'\0' || reg_noteol) \ | |||
| && (next_c != L'\n' || !reg_newline)) \ | |||
| || ((assertions & ASSERT_AT_BOW) \ | |||
| && (IS_WORD_CHAR(prev_c) || !IS_WORD_CHAR(next_c))) \ | |||
| || ((assertions & ASSERT_AT_EOW) \ | |||
| && (!IS_WORD_CHAR(prev_c) || IS_WORD_CHAR(next_c))) \ | |||
| || ((assertions & ASSERT_AT_WB) \ | |||
| && (pos != 0 && next_c != L'\0' \ | |||
| && IS_WORD_CHAR(prev_c) == IS_WORD_CHAR(next_c))) \ | |||
| || ((assertions & ASSERT_AT_WB_NEG) \ | |||
| && (pos == 0 || next_c == L'\0' \ | |||
| || IS_WORD_CHAR(prev_c) != IS_WORD_CHAR(next_c)))) | |||
| #define CHECK_CHAR_CLASSES(trans_i, tnfa, eflags) \ | |||
| (((trans_i->assertions & ASSERT_CHAR_CLASS) \ | |||
| && !(tnfa->cflags & REG_ICASE) \ | |||
| && !tre_isctype((tre_cint_t)prev_c, trans_i->u.class)) \ | |||
| || ((trans_i->assertions & ASSERT_CHAR_CLASS) \ | |||
| && (tnfa->cflags & REG_ICASE) \ | |||
| && !tre_isctype(tre_tolower((tre_cint_t)prev_c),trans_i->u.class) \ | |||
| && !tre_isctype(tre_toupper((tre_cint_t)prev_c),trans_i->u.class)) \ | |||
| || ((trans_i->assertions & ASSERT_CHAR_CLASS_NEG) \ | |||
| && tre_neg_char_classes_match(trans_i->neg_classes,(tre_cint_t)prev_c,\ | |||
| tnfa->cflags & REG_ICASE))) | |||
| /* Returns 1 if `t1' wins `t2', 0 otherwise. */ | |||
| inline static int | |||
| tre_tag_order(int num_tags, tre_tag_direction_t *tag_directions, | |||
| int *t1, int *t2) | |||
| { | |||
| int i; | |||
| for (i = 0; i < num_tags; i++) | |||
| { | |||
| if (tag_directions[i] == TRE_TAG_MINIMIZE) | |||
| { | |||
| if (t1[i] < t2[i]) | |||
| return 1; | |||
| if (t1[i] > t2[i]) | |||
| return 0; | |||
| } | |||
| else | |||
| { | |||
| if (t1[i] > t2[i]) | |||
| return 1; | |||
| if (t1[i] < t2[i]) | |||
| return 0; | |||
| } | |||
| } | |||
| /* assert(0);*/ | |||
| return 0; | |||
| } | |||
| inline static int | |||
| tre_neg_char_classes_match(tre_ctype_t *classes, tre_cint_t wc, int icase) | |||
| { | |||
| DPRINT(("neg_char_classes_test: %p, %d, %d\n", classes, wc, icase)); | |||
| while (*classes != (tre_ctype_t)0) | |||
| if ((!icase && tre_isctype(wc, *classes)) | |||
| || (icase && (tre_isctype(tre_toupper(wc), *classes) | |||
| || tre_isctype(tre_tolower(wc), *classes)))) | |||
| return 1; /* Match. */ | |||
| else | |||
| classes++; | |||
| return 0; /* No match. */ | |||
| } | |||
| @@ -0,0 +1,155 @@ | |||
| /* | |||
| tre-mem.c - TRE memory allocator | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| /* | |||
| This memory allocator is for allocating small memory blocks efficiently | |||
| in terms of memory overhead and execution speed. The allocated blocks | |||
| cannot be freed individually, only all at once. There can be multiple | |||
| allocators, though. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <stdlib.h> | |||
| #include <string.h> | |||
| #include "tre-internal.h" | |||
| #include "tre-mem.h" | |||
| #include "xmalloc.h" | |||
| /* Returns a new memory allocator or NULL if out of memory. */ | |||
| tre_mem_t | |||
| tre_mem_new_impl(int provided, void *provided_block) | |||
| { | |||
| tre_mem_t mem; | |||
| if (provided) | |||
| { | |||
| mem = provided_block; | |||
| memset(mem, 0, sizeof(*mem)); | |||
| } | |||
| else | |||
| mem = xcalloc(1, sizeof(*mem)); | |||
| if (mem == NULL) | |||
| return NULL; | |||
| return mem; | |||
| } | |||
| /* Frees the memory allocator and all memory allocated with it. */ | |||
| void | |||
| tre_mem_destroy(tre_mem_t mem) | |||
| { | |||
| tre_list_t *tmp, *l = mem->blocks; | |||
| while (l != NULL) | |||
| { | |||
| xfree(l->data); | |||
| tmp = l->next; | |||
| xfree(l); | |||
| l = tmp; | |||
| } | |||
| xfree(mem); | |||
| } | |||
| /* Allocates a block of `size' bytes from `mem'. Returns a pointer to the | |||
| allocated block or NULL if an underlying malloc() failed. */ | |||
| void * | |||
| tre_mem_alloc_impl(tre_mem_t mem, int provided, void *provided_block, | |||
| int zero, size_t size) | |||
| { | |||
| void *ptr; | |||
| if (mem->failed) | |||
| { | |||
| DPRINT(("tre_mem_alloc: oops, called after failure?!\n")); | |||
| return NULL; | |||
| } | |||
| #ifdef MALLOC_DEBUGGING | |||
| if (!provided) | |||
| { | |||
| ptr = xmalloc(1); | |||
| if (ptr == NULL) | |||
| { | |||
| DPRINT(("tre_mem_alloc: xmalloc forced failure\n")); | |||
| mem->failed = 1; | |||
| return NULL; | |||
| } | |||
| xfree(ptr); | |||
| } | |||
| #endif /* MALLOC_DEBUGGING */ | |||
| if (mem->n < size) | |||
| { | |||
| /* We need more memory than is available in the current block. | |||
| Allocate a new block. */ | |||
| tre_list_t *l; | |||
| if (provided) | |||
| { | |||
| DPRINT(("tre_mem_alloc: using provided block\n")); | |||
| if (provided_block == NULL) | |||
| { | |||
| DPRINT(("tre_mem_alloc: provided block was NULL\n")); | |||
| mem->failed = 1; | |||
| return NULL; | |||
| } | |||
| mem->ptr = provided_block; | |||
| mem->n = TRE_MEM_BLOCK_SIZE; | |||
| } | |||
| else | |||
| { | |||
| int block_size; | |||
| if (size * 8 > TRE_MEM_BLOCK_SIZE) | |||
| block_size = size * 8; | |||
| else | |||
| block_size = TRE_MEM_BLOCK_SIZE; | |||
| DPRINT(("tre_mem_alloc: allocating new %d byte block\n", | |||
| block_size)); | |||
| l = xmalloc(sizeof(*l)); | |||
| if (l == NULL) | |||
| { | |||
| mem->failed = 1; | |||
| return NULL; | |||
| } | |||
| l->data = xmalloc(block_size); | |||
| if (l->data == NULL) | |||
| { | |||
| xfree(l); | |||
| mem->failed = 1; | |||
| return NULL; | |||
| } | |||
| l->next = NULL; | |||
| if (mem->current != NULL) | |||
| mem->current->next = l; | |||
| if (mem->blocks == NULL) | |||
| mem->blocks = l; | |||
| mem->current = l; | |||
| mem->ptr = l->data; | |||
| mem->n = block_size; | |||
| } | |||
| } | |||
| /* Make sure the next pointer will be aligned. */ | |||
| size += ALIGN(mem->ptr + size, long); | |||
| /* Allocate from current block. */ | |||
| ptr = mem->ptr; | |||
| mem->ptr += size; | |||
| mem->n -= size; | |||
| /* Set to zero if needed. */ | |||
| if (zero) | |||
| memset(ptr, 0, size); | |||
| return ptr; | |||
| } | |||
| /* EOF */ | |||
| @@ -0,0 +1,66 @@ | |||
| /* | |||
| tre-mem.h - TRE memory allocator interface | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_MEM_H | |||
| #define TRE_MEM_H 1 | |||
| #include <stdlib.h> | |||
| #define TRE_MEM_BLOCK_SIZE 1024 | |||
| typedef struct tre_list { | |||
| void *data; | |||
| struct tre_list *next; | |||
| } tre_list_t; | |||
| typedef struct tre_mem_struct { | |||
| tre_list_t *blocks; | |||
| tre_list_t *current; | |||
| char *ptr; | |||
| size_t n; | |||
| int failed; | |||
| void **provided; | |||
| } *tre_mem_t; | |||
| tre_mem_t tre_mem_new_impl(int provided, void *provided_block); | |||
| void *tre_mem_alloc_impl(tre_mem_t mem, int provided, void *provided_block, | |||
| int zero, size_t size); | |||
| /* Returns a new memory allocator or NULL if out of memory. */ | |||
| #define tre_mem_new() tre_mem_new_impl(0, NULL) | |||
| /* Allocates a block of `size' bytes from `mem'. Returns a pointer to the | |||
| allocated block or NULL if an underlying malloc() failed. */ | |||
| #define tre_mem_alloc(mem, size) tre_mem_alloc_impl(mem, 0, NULL, 0, size) | |||
| /* Allocates a block of `size' bytes from `mem'. Returns a pointer to the | |||
| allocated block or NULL if an underlying malloc() failed. The memory | |||
| is set to zero. */ | |||
| #define tre_mem_calloc(mem, size) tre_mem_alloc_impl(mem, 0, NULL, 1, size) | |||
| #ifdef TRE_USE_ALLOCA | |||
| /* alloca() versions. Like above, but memory is allocated with alloca() | |||
| instead of malloc(). */ | |||
| #define tre_mem_newa() \ | |||
| tre_mem_new_impl(1, alloca(sizeof(struct tre_mem_struct))) | |||
| #define tre_mem_alloca(mem, size) \ | |||
| ((mem)->n >= (size) \ | |||
| ? tre_mem_alloc_impl((mem), 1, NULL, 0, (size)) \ | |||
| : tre_mem_alloc_impl((mem), 1, alloca(TRE_MEM_BLOCK_SIZE), 0, (size))) | |||
| #endif /* TRE_USE_ALLOCA */ | |||
| /* Frees the memory allocator and all memory allocated with it. */ | |||
| void tre_mem_destroy(tre_mem_t mem); | |||
| #endif /* TRE_MEM_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,50 @@ | |||
| /* | |||
| tre-parse.c - Regexp parser definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_PARSE_H | |||
| #define TRE_PARSE_H 1 | |||
| /* Parse context. */ | |||
| typedef struct { | |||
| /* Memory allocator. The AST is allocated using this. */ | |||
| tre_mem_t mem; | |||
| /* Stack used for keeping track of regexp syntax. */ | |||
| tre_stack_t *stack; | |||
| /* The parse result. */ | |||
| tre_ast_node_t *result; | |||
| /* The regexp to parse and its length. */ | |||
| const tre_char_t *re; | |||
| /* The first character of the entire regexp. */ | |||
| const tre_char_t *re_start; | |||
| /* The first character after the end of the regexp. */ | |||
| const tre_char_t *re_end; | |||
| int len; | |||
| /* Current submatch ID. */ | |||
| int submatch_id; | |||
| /* Current position (number of literal). */ | |||
| int position; | |||
| /* The highest back reference or -1 if none seen so far. */ | |||
| int max_backref; | |||
| /* This flag is set if the regexp uses approximate matching. */ | |||
| int have_approx; | |||
| /* Compilation flags. */ | |||
| int cflags; | |||
| /* If this flag is set the top-level submatch is not captured. */ | |||
| int nofirstsub; | |||
| /* The currently set approximate matching parameters. */ | |||
| int params[TRE_PARAM_LAST]; | |||
| } tre_parse_ctx_t; | |||
| /* Parses a wide character regexp pattern into a syntax tree. This parser | |||
| handles both syntaxes (BRE and ERE), including the TRE extensions. */ | |||
| reg_errcode_t | |||
| tre_parse(tre_parse_ctx_t *ctx); | |||
| #endif /* TRE_PARSE_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,125 @@ | |||
| /* | |||
| tre-stack.c - Simple stack implementation | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <stdlib.h> | |||
| #include <assert.h> | |||
| #include "tre-internal.h" | |||
| #include "tre-stack.h" | |||
| #include "xmalloc.h" | |||
| union tre_stack_item { | |||
| void *voidptr_value; | |||
| int int_value; | |||
| }; | |||
| struct tre_stack_rec { | |||
| int size; | |||
| int max_size; | |||
| int increment; | |||
| int ptr; | |||
| union tre_stack_item *stack; | |||
| }; | |||
| tre_stack_t * | |||
| tre_stack_new(int size, int max_size, int increment) | |||
| { | |||
| tre_stack_t *s; | |||
| s = xmalloc(sizeof(*s)); | |||
| if (s != NULL) | |||
| { | |||
| s->stack = xmalloc(sizeof(*s->stack) * size); | |||
| if (s->stack == NULL) | |||
| { | |||
| xfree(s); | |||
| return NULL; | |||
| } | |||
| s->size = size; | |||
| s->max_size = max_size; | |||
| s->increment = increment; | |||
| s->ptr = 0; | |||
| } | |||
| return s; | |||
| } | |||
| void | |||
| tre_stack_destroy(tre_stack_t *s) | |||
| { | |||
| xfree(s->stack); | |||
| xfree(s); | |||
| } | |||
| int | |||
| tre_stack_num_objects(tre_stack_t *s) | |||
| { | |||
| return s->ptr; | |||
| } | |||
| static reg_errcode_t | |||
| tre_stack_push(tre_stack_t *s, union tre_stack_item value) | |||
| { | |||
| if (s->ptr < s->size) | |||
| { | |||
| s->stack[s->ptr] = value; | |||
| s->ptr++; | |||
| } | |||
| else | |||
| { | |||
| if (s->size >= s->max_size) | |||
| { | |||
| DPRINT(("tre_stack_push: stack full\n")); | |||
| return REG_ESPACE; | |||
| } | |||
| else | |||
| { | |||
| union tre_stack_item *new_buffer; | |||
| int new_size; | |||
| DPRINT(("tre_stack_push: trying to realloc more space\n")); | |||
| new_size = s->size + s->increment; | |||
| if (new_size > s->max_size) | |||
| new_size = s->max_size; | |||
| new_buffer = xrealloc(s->stack, sizeof(*new_buffer) * new_size); | |||
| if (new_buffer == NULL) | |||
| { | |||
| DPRINT(("tre_stack_push: realloc failed.\n")); | |||
| return REG_ESPACE; | |||
| } | |||
| DPRINT(("tre_stack_push: realloc succeeded.\n")); | |||
| assert(new_size > s->size); | |||
| s->size = new_size; | |||
| s->stack = new_buffer; | |||
| tre_stack_push(s, value); | |||
| } | |||
| } | |||
| return REG_OK; | |||
| } | |||
| #define define_pushf(typetag, type) \ | |||
| declare_pushf(typetag, type) { \ | |||
| union tre_stack_item item; \ | |||
| item.typetag ## _value = value; \ | |||
| return tre_stack_push(s, item); \ | |||
| } | |||
| define_pushf(int, int) | |||
| define_pushf(voidptr, void *) | |||
| #define define_popf(typetag, type) \ | |||
| declare_popf(typetag, type) { \ | |||
| return s->stack[--s->ptr].typetag ## _value; \ | |||
| } | |||
| define_popf(int, int) | |||
| define_popf(voidptr, void *) | |||
| /* EOF */ | |||
| @@ -0,0 +1,76 @@ | |||
| /* | |||
| tre-stack.h: Stack definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_STACK_H | |||
| #define TRE_STACK_H 1 | |||
| #include "tre.h" | |||
| typedef struct tre_stack_rec tre_stack_t; | |||
| /* Creates a new stack object. `size' is initial size in bytes, `max_size' | |||
| is maximum size, and `increment' specifies how much more space will be | |||
| allocated with realloc() if all space gets used up. Returns the stack | |||
| object or NULL if out of memory. */ | |||
| tre_stack_t * | |||
| tre_stack_new(int size, int max_size, int increment); | |||
| /* Frees the stack object. */ | |||
| void | |||
| tre_stack_destroy(tre_stack_t *s); | |||
| /* Returns the current number of objects in the stack. */ | |||
| int | |||
| tre_stack_num_objects(tre_stack_t *s); | |||
| /* Each tre_stack_push_*(tre_stack_t *s, <type> value) function pushes | |||
| `value' on top of stack `s'. Returns REG_ESPACE if out of memory. | |||
| This tries to realloc() more space before failing if maximum size | |||
| has not yet been reached. Returns REG_OK if successful. */ | |||
| #define declare_pushf(typetag, type) \ | |||
| reg_errcode_t tre_stack_push_ ## typetag(tre_stack_t *s, type value) | |||
| declare_pushf(voidptr, void *); | |||
| declare_pushf(int, int); | |||
| /* Each tre_stack_pop_*(tre_stack_t *s) function pops the topmost | |||
| element off of stack `s' and returns it. The stack must not be | |||
| empty. */ | |||
| #define declare_popf(typetag, type) \ | |||
| type tre_stack_pop_ ## typetag(tre_stack_t *s) | |||
| declare_popf(voidptr, void *); | |||
| declare_popf(int, int); | |||
| /* Just to save some typing. */ | |||
| #define STACK_PUSH(s, typetag, value) \ | |||
| do \ | |||
| { \ | |||
| status = tre_stack_push_ ## typetag(s, value); \ | |||
| } \ | |||
| while (/*CONSTCOND*/0) | |||
| #define STACK_PUSHX(s, typetag, value) \ | |||
| { \ | |||
| status = tre_stack_push_ ## typetag(s, value); \ | |||
| if (status != REG_OK) \ | |||
| break; \ | |||
| } | |||
| #define STACK_PUSHR(s, typetag, value) \ | |||
| { \ | |||
| reg_errcode_t _status; \ | |||
| _status = tre_stack_push_ ## typetag(s, value); \ | |||
| if (_status != REG_OK) \ | |||
| return _status; \ | |||
| } | |||
| #endif /* TRE_STACK_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,276 @@ | |||
| /* | |||
| tre.h - TRE public API definitions | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef TRE_H | |||
| #define TRE_H 1 | |||
| #include "tre-config.h" | |||
| #ifdef HAVE_SYS_TYPES_H | |||
| #include <sys/types.h> | |||
| #endif /* HAVE_SYS_TYPES_H */ | |||
| #ifdef HAVE_LIBUTF8_H | |||
| #include <libutf8.h> | |||
| #endif /* HAVE_LIBUTF8_H */ | |||
| #ifdef TRE_USE_SYSTEM_REGEX_H | |||
| /* Include the system regex.h to make TRE ABI compatible with the | |||
| system regex. */ | |||
| #include TRE_SYSTEM_REGEX_H_PATH | |||
| #define tre_regcomp regcomp | |||
| #define tre_regexec regexec | |||
| #define tre_regerror regerror | |||
| #define tre_regfree regfree | |||
| #endif /* TRE_USE_SYSTEM_REGEX_H */ | |||
| #ifdef __cplusplus | |||
| extern "C" { | |||
| #endif | |||
| #ifdef TRE_USE_SYSTEM_REGEX_H | |||
| #ifndef REG_OK | |||
| #define REG_OK 0 | |||
| #endif /* !REG_OK */ | |||
| #ifndef HAVE_REG_ERRCODE_T | |||
| typedef int reg_errcode_t; | |||
| #endif /* !HAVE_REG_ERRCODE_T */ | |||
| #if !defined(REG_NOSPEC) && !defined(REG_LITERAL) | |||
| #define REG_LITERAL 0x1000 | |||
| #endif | |||
| /* Extra tre_regcomp() flags. */ | |||
| #ifndef REG_BASIC | |||
| #define REG_BASIC 0 | |||
| #endif /* !REG_BASIC */ | |||
| #define REG_RIGHT_ASSOC (REG_LITERAL << 1) | |||
| #define REG_UNGREEDY (REG_RIGHT_ASSOC << 1) | |||
| /* Extra tre_regexec() flags. */ | |||
| #define REG_APPROX_MATCHER 0x1000 | |||
| #define REG_BACKTRACKING_MATCHER (REG_APPROX_MATCHER << 1) | |||
| #else /* !TRE_USE_SYSTEM_REGEX_H */ | |||
| /* If the we're not using system regex.h, we need to define the | |||
| structs and enums ourselves. */ | |||
| typedef int regoff_t; | |||
| typedef struct { | |||
| size_t re_nsub; /* Number of parenthesized subexpressions. */ | |||
| void *value; /* For internal use only. */ | |||
| } regex_t; | |||
| typedef struct { | |||
| regoff_t rm_so; | |||
| regoff_t rm_eo; | |||
| } regmatch_t; | |||
| typedef enum { | |||
| REG_OK = 0, /* No error. */ | |||
| /* POSIX tre_regcomp() return error codes. (In the order listed in the | |||
| standard.) */ | |||
| REG_NOMATCH, /* No match. */ | |||
| REG_BADPAT, /* Invalid regexp. */ | |||
| REG_ECOLLATE, /* Unknown collating element. */ | |||
| REG_ECTYPE, /* Unknown character class name. */ | |||
| REG_EESCAPE, /* Trailing backslash. */ | |||
| REG_ESUBREG, /* Invalid back reference. */ | |||
| REG_EBRACK, /* "[]" imbalance */ | |||
| REG_EPAREN, /* "\(\)" or "()" imbalance */ | |||
| REG_EBRACE, /* "\{\}" or "{}" imbalance */ | |||
| REG_BADBR, /* Invalid content of {} */ | |||
| REG_ERANGE, /* Invalid use of range operator */ | |||
| REG_ESPACE, /* Out of memory. */ | |||
| REG_BADRPT /* Invalid use of repetition operators. */ | |||
| } reg_errcode_t; | |||
| /* POSIX tre_regcomp() flags. */ | |||
| #define REG_EXTENDED 1 | |||
| #define REG_ICASE (REG_EXTENDED << 1) | |||
| #define REG_NEWLINE (REG_ICASE << 1) | |||
| #define REG_NOSUB (REG_NEWLINE << 1) | |||
| /* Extra tre_regcomp() flags. */ | |||
| #define REG_BASIC 0 | |||
| #define REG_LITERAL (REG_NOSUB << 1) | |||
| #define REG_RIGHT_ASSOC (REG_LITERAL << 1) | |||
| #define REG_UNGREEDY (REG_RIGHT_ASSOC << 1) | |||
| /* POSIX tre_regexec() flags. */ | |||
| #define REG_NOTBOL 1 | |||
| #define REG_NOTEOL (REG_NOTBOL << 1) | |||
| /* Extra tre_regexec() flags. */ | |||
| #define REG_APPROX_MATCHER (REG_NOTEOL << 1) | |||
| #define REG_BACKTRACKING_MATCHER (REG_APPROX_MATCHER << 1) | |||
| #endif /* !TRE_USE_SYSTEM_REGEX_H */ | |||
| /* REG_NOSPEC and REG_LITERAL mean the same thing. */ | |||
| #if defined(REG_LITERAL) && !defined(REG_NOSPEC) | |||
| #define REG_NOSPEC REG_LITERAL | |||
| #elif defined(REG_NOSPEC) && !defined(REG_LITERAL) | |||
| #define REG_LITERAL REG_NOSPEC | |||
| #endif /* defined(REG_NOSPEC) */ | |||
| /* The maximum number of iterations in a bound expression. */ | |||
| #undef RE_DUP_MAX | |||
| #define RE_DUP_MAX 255 | |||
| /* The POSIX.2 regexp functions */ | |||
| extern int | |||
| tre_regcomp(regex_t *preg, const char *regex, int cflags); | |||
| extern int | |||
| tre_regexec(const regex_t *preg, const char *string, size_t nmatch, | |||
| regmatch_t pmatch[], int eflags); | |||
| extern size_t | |||
| tre_regerror(int errcode, const regex_t *preg, char *errbuf, | |||
| size_t errbuf_size); | |||
| extern void | |||
| tre_regfree(regex_t *preg); | |||
| #ifdef TRE_WCHAR | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif /* HAVE_WCHAR_H */ | |||
| /* Wide character versions (not in POSIX.2). */ | |||
| extern int | |||
| tre_regwcomp(regex_t *preg, const wchar_t *regex, int cflags); | |||
| extern int | |||
| tre_regwexec(const regex_t *preg, const wchar_t *string, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags); | |||
| #endif /* TRE_WCHAR */ | |||
| /* Versions with a maximum length argument and therefore the capability to | |||
| handle null characters in the middle of the strings (not in POSIX.2). */ | |||
| extern int | |||
| tre_regncomp(regex_t *preg, const char *regex, size_t len, int cflags); | |||
| extern int | |||
| tre_regnexec(const regex_t *preg, const char *string, size_t len, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags); | |||
| #ifdef TRE_WCHAR | |||
| extern int | |||
| tre_regwncomp(regex_t *preg, const wchar_t *regex, size_t len, int cflags); | |||
| extern int | |||
| tre_regwnexec(const regex_t *preg, const wchar_t *string, size_t len, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags); | |||
| #endif /* TRE_WCHAR */ | |||
| #ifdef TRE_APPROX | |||
| /* Approximate matching parameter struct. */ | |||
| typedef struct { | |||
| int cost_ins; /* Default cost of an inserted character. */ | |||
| int cost_del; /* Default cost of a deleted character. */ | |||
| int cost_subst; /* Default cost of a substituted character. */ | |||
| int max_cost; /* Maximum allowed cost of a match. */ | |||
| int max_ins; /* Maximum allowed number of inserts. */ | |||
| int max_del; /* Maximum allowed number of deletes. */ | |||
| int max_subst; /* Maximum allowed number of substitutes. */ | |||
| int max_err; /* Maximum allowed number of errors total. */ | |||
| } regaparams_t; | |||
| /* Approximate matching result struct. */ | |||
| typedef struct { | |||
| size_t nmatch; /* Length of pmatch[] array. */ | |||
| regmatch_t *pmatch; /* Submatch data. */ | |||
| int cost; /* Cost of the match. */ | |||
| int num_ins; /* Number of inserts in the match. */ | |||
| int num_del; /* Number of deletes in the match. */ | |||
| int num_subst; /* Number of substitutes in the match. */ | |||
| } regamatch_t; | |||
| /* Approximate matching functions. */ | |||
| extern int | |||
| tre_regaexec(const regex_t *preg, const char *string, | |||
| regamatch_t *match, regaparams_t params, int eflags); | |||
| extern int | |||
| tre_reganexec(const regex_t *preg, const char *string, size_t len, | |||
| regamatch_t *match, regaparams_t params, int eflags); | |||
| #ifdef TRE_WCHAR | |||
| /* Wide character approximate matching. */ | |||
| extern int | |||
| tre_regawexec(const regex_t *preg, const wchar_t *string, | |||
| regamatch_t *match, regaparams_t params, int eflags); | |||
| extern int | |||
| tre_regawnexec(const regex_t *preg, const wchar_t *string, size_t len, | |||
| regamatch_t *match, regaparams_t params, int eflags); | |||
| #endif /* TRE_WCHAR */ | |||
| /* Sets the parameters to default values. */ | |||
| extern void | |||
| tre_regaparams_default(regaparams_t *params); | |||
| #endif /* TRE_APPROX */ | |||
| #ifdef TRE_WCHAR | |||
| typedef wchar_t tre_char_t; | |||
| #else /* !TRE_WCHAR */ | |||
| typedef unsigned char tre_char_t; | |||
| #endif /* !TRE_WCHAR */ | |||
| typedef struct { | |||
| int (*get_next_char)(tre_char_t *c, unsigned int *pos_add, void *context); | |||
| void (*rewind)(size_t pos, void *context); | |||
| int (*compare)(size_t pos1, size_t pos2, size_t len, void *context); | |||
| void *context; | |||
| } tre_str_source; | |||
| extern int | |||
| tre_reguexec(const regex_t *preg, const tre_str_source *string, | |||
| size_t nmatch, regmatch_t pmatch[], int eflags); | |||
| /* Returns the version string. The returned string is static. */ | |||
| extern char * | |||
| tre_version(void); | |||
| /* Returns the value for a config parameter. The type to which `result' | |||
| must point to depends of the value of `query', see documentation for | |||
| more details. */ | |||
| extern int | |||
| tre_config(int query, void *result); | |||
| enum { | |||
| TRE_CONFIG_APPROX, | |||
| TRE_CONFIG_WCHAR, | |||
| TRE_CONFIG_MULTIBYTE, | |||
| TRE_CONFIG_SYSTEM_ABI, | |||
| TRE_CONFIG_VERSION | |||
| }; | |||
| /* Returns 1 if the compiled pattern has back references, 0 if not. */ | |||
| extern int | |||
| tre_have_backrefs(const regex_t *preg); | |||
| /* Returns 1 if the compiled pattern uses approximate matching features, | |||
| 0 if not. */ | |||
| extern int | |||
| tre_have_approx(const regex_t *preg); | |||
| #ifdef __cplusplus | |||
| } | |||
| #endif | |||
| #endif /* TRE_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,351 @@ | |||
| /* | |||
| xmalloc.c - Simple malloc debugging library implementation | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| /* | |||
| TODO: | |||
| - red zones | |||
| - group dumps by source location | |||
| */ | |||
| #ifdef HAVE_CONFIG_H | |||
| #include <config.h> | |||
| #endif /* HAVE_CONFIG_H */ | |||
| #include <stdlib.h> | |||
| #include <assert.h> | |||
| #include <stdio.h> | |||
| #define XMALLOC_INTERNAL 1 | |||
| #include "xmalloc.h" | |||
| /* | |||
| Internal stuff. | |||
| */ | |||
| typedef struct hashTableItemRec { | |||
| void *ptr; | |||
| int bytes; | |||
| const char *file; | |||
| int line; | |||
| const char *func; | |||
| struct hashTableItemRec *next; | |||
| } hashTableItem; | |||
| typedef struct { | |||
| hashTableItem **table; | |||
| } hashTable; | |||
| static int xmalloc_peak; | |||
| int xmalloc_current; | |||
| static int xmalloc_peak_blocks; | |||
| int xmalloc_current_blocks; | |||
| static int xmalloc_fail_after; | |||
| #define TABLE_BITS 8 | |||
| #define TABLE_MASK ((1 << TABLE_BITS) - 1) | |||
| #define TABLE_SIZE (1 << TABLE_BITS) | |||
| static hashTable * | |||
| hash_table_new(void) | |||
| { | |||
| hashTable *tbl; | |||
| tbl = malloc(sizeof(*tbl)); | |||
| if (tbl != NULL) | |||
| { | |||
| tbl->table = calloc(TABLE_SIZE, sizeof(*tbl->table)); | |||
| if (tbl->table == NULL) | |||
| { | |||
| free(tbl); | |||
| return NULL; | |||
| } | |||
| } | |||
| return tbl; | |||
| } | |||
| static int | |||
| hash_void_ptr(void *ptr) | |||
| { | |||
| int hash; | |||
| int i; | |||
| /* I took this hash function just off the top of my head, I have | |||
| no idea whether it is bad or very bad. */ | |||
| hash = 0; | |||
| for (i = 0; i < (int)sizeof(ptr)*8 / TABLE_BITS; i++) | |||
| { | |||
| hash ^= (unsigned long)ptr >> i*8; | |||
| hash += i * 17; | |||
| hash &= TABLE_MASK; | |||
| } | |||
| return hash; | |||
| } | |||
| static void | |||
| hash_table_add(hashTable *tbl, void *ptr, int bytes, | |||
| const char *file, int line, const char *func) | |||
| { | |||
| int i; | |||
| hashTableItem *item, *new; | |||
| i = hash_void_ptr(ptr); | |||
| item = tbl->table[i]; | |||
| if (item != NULL) | |||
| while (item->next != NULL) | |||
| item = item->next; | |||
| new = malloc(sizeof(*new)); | |||
| assert(new != NULL); | |||
| new->ptr = ptr; | |||
| new->bytes = bytes; | |||
| new->file = file; | |||
| new->line = line; | |||
| new->func = func; | |||
| new->next = NULL; | |||
| if (item != NULL) | |||
| item->next = new; | |||
| else | |||
| tbl->table[i] = new; | |||
| xmalloc_current += bytes; | |||
| if (xmalloc_current > xmalloc_peak) | |||
| xmalloc_peak = xmalloc_current; | |||
| xmalloc_current_blocks++; | |||
| if (xmalloc_current_blocks > xmalloc_peak_blocks) | |||
| xmalloc_peak_blocks = xmalloc_current_blocks; | |||
| } | |||
| static void | |||
| hash_table_del(hashTable *tbl, void *ptr) | |||
| { | |||
| int i; | |||
| hashTableItem *item, *prev; | |||
| i = hash_void_ptr(ptr); | |||
| item = tbl->table[i]; | |||
| if (item == NULL) | |||
| { | |||
| printf("xfree: invalid ptr %p\n", ptr); | |||
| abort(); | |||
| } | |||
| prev = NULL; | |||
| while (item->ptr != ptr) | |||
| { | |||
| prev = item; | |||
| item = item->next; | |||
| } | |||
| if (item->ptr != ptr) | |||
| { | |||
| printf("xfree: invalid ptr %p\n", ptr); | |||
| abort(); | |||
| } | |||
| xmalloc_current -= item->bytes; | |||
| xmalloc_current_blocks--; | |||
| if (prev != NULL) | |||
| { | |||
| prev->next = item->next; | |||
| free(item); | |||
| } | |||
| else | |||
| { | |||
| tbl->table[i] = item->next; | |||
| free(item); | |||
| } | |||
| } | |||
| static hashTable *xmalloc_table = NULL; | |||
| static void | |||
| xmalloc_init(void) | |||
| { | |||
| if (xmalloc_table == NULL) | |||
| { | |||
| xmalloc_table = hash_table_new(); | |||
| xmalloc_peak = 0; | |||
| xmalloc_peak_blocks = 0; | |||
| xmalloc_current = 0; | |||
| xmalloc_current_blocks = 0; | |||
| xmalloc_fail_after = -1; | |||
| } | |||
| assert(xmalloc_table != NULL); | |||
| assert(xmalloc_table->table != NULL); | |||
| } | |||
| /* | |||
| Public API. | |||
| */ | |||
| void | |||
| xmalloc_configure(int fail_after) | |||
| { | |||
| xmalloc_init(); | |||
| xmalloc_fail_after = fail_after; | |||
| } | |||
| int | |||
| xmalloc_dump_leaks(void) | |||
| { | |||
| int i; | |||
| int num_leaks = 0; | |||
| int leaked_bytes = 0; | |||
| hashTableItem *item; | |||
| xmalloc_init(); | |||
| for (i = 0; i < TABLE_SIZE; i++) | |||
| { | |||
| item = xmalloc_table->table[i]; | |||
| while (item != NULL) | |||
| { | |||
| printf("%s:%d: %s: %d bytes at %p not freed\n", | |||
| item->file, item->line, item->func, item->bytes, item->ptr); | |||
| num_leaks++; | |||
| leaked_bytes += item->bytes; | |||
| item = item->next; | |||
| } | |||
| } | |||
| if (num_leaks == 0) | |||
| printf("No memory leaks.\n"); | |||
| else | |||
| printf("%d unfreed memory chuncks, total %d unfreed bytes.\n", | |||
| num_leaks, leaked_bytes); | |||
| printf("Peak memory consumption %d bytes (%.1f kB, %.1f MB) in %d blocks ", | |||
| xmalloc_peak, (double)xmalloc_peak / 1024, | |||
| (double)xmalloc_peak / (1024*1024), xmalloc_peak_blocks); | |||
| printf("(average "); | |||
| if (xmalloc_peak_blocks) | |||
| printf("%d", ((xmalloc_peak + xmalloc_peak_blocks / 2) | |||
| / xmalloc_peak_blocks)); | |||
| else | |||
| printf("N/A"); | |||
| printf(" bytes per block).\n"); | |||
| return num_leaks; | |||
| } | |||
| void * | |||
| xmalloc_impl(size_t size, const char *file, int line, const char *func) | |||
| { | |||
| void *ptr; | |||
| xmalloc_init(); | |||
| assert(size > 0); | |||
| if (xmalloc_fail_after == 0) | |||
| { | |||
| xmalloc_fail_after = -2; | |||
| #if 0 | |||
| printf("xmalloc: forced failure %s:%d: %s\n", file, line, func); | |||
| #endif | |||
| return NULL; | |||
| } | |||
| else if (xmalloc_fail_after == -2) | |||
| { | |||
| printf("xmalloc: called after failure from %s:%d: %s\n", | |||
| file, line, func); | |||
| assert(0); | |||
| } | |||
| else if (xmalloc_fail_after > 0) | |||
| xmalloc_fail_after--; | |||
| ptr = malloc(size); | |||
| if (ptr != NULL) | |||
| hash_table_add(xmalloc_table, ptr, (int)size, file, line, func); | |||
| return ptr; | |||
| } | |||
| void * | |||
| xcalloc_impl(size_t nmemb, size_t size, const char *file, int line, | |||
| const char *func) | |||
| { | |||
| void *ptr; | |||
| xmalloc_init(); | |||
| assert(size > 0); | |||
| if (xmalloc_fail_after == 0) | |||
| { | |||
| xmalloc_fail_after = -2; | |||
| #if 0 | |||
| printf("xcalloc: forced failure %s:%d: %s\n", file, line, func); | |||
| #endif | |||
| return NULL; | |||
| } | |||
| else if (xmalloc_fail_after == -2) | |||
| { | |||
| printf("xcalloc: called after failure from %s:%d: %s\n", | |||
| file, line, func); | |||
| assert(0); | |||
| } | |||
| else if (xmalloc_fail_after > 0) | |||
| xmalloc_fail_after--; | |||
| ptr = calloc(nmemb, size); | |||
| if (ptr != NULL) | |||
| hash_table_add(xmalloc_table, ptr, (int)(nmemb * size), file, line, func); | |||
| return ptr; | |||
| } | |||
| void | |||
| xfree_impl(void *ptr, const char *file, int line, const char *func) | |||
| { | |||
| /*LINTED*/(void)&file; | |||
| /*LINTED*/(void)&line; | |||
| /*LINTED*/(void)&func; | |||
| xmalloc_init(); | |||
| if (ptr != NULL) | |||
| hash_table_del(xmalloc_table, ptr); | |||
| free(ptr); | |||
| } | |||
| void * | |||
| xrealloc_impl(void *ptr, size_t new_size, const char *file, int line, | |||
| const char *func) | |||
| { | |||
| void *new_ptr; | |||
| xmalloc_init(); | |||
| assert(ptr != NULL); | |||
| assert(new_size > 0); | |||
| if (xmalloc_fail_after == 0) | |||
| { | |||
| xmalloc_fail_after = -2; | |||
| return NULL; | |||
| } | |||
| else if (xmalloc_fail_after == -2) | |||
| { | |||
| printf("xrealloc: called after failure from %s:%d: %s\n", | |||
| file, line, func); | |||
| assert(0); | |||
| } | |||
| else if (xmalloc_fail_after > 0) | |||
| xmalloc_fail_after--; | |||
| new_ptr = realloc(ptr, new_size); | |||
| if (new_ptr != NULL) | |||
| { | |||
| hash_table_del(xmalloc_table, ptr); | |||
| hash_table_add(xmalloc_table, new_ptr, (int)new_size, file, line, func); | |||
| } | |||
| return new_ptr; | |||
| } | |||
| /* EOF */ | |||
| @@ -0,0 +1,77 @@ | |||
| /* | |||
| xmalloc.h - Simple malloc debugging library API | |||
| This software is released under a BSD-style license. | |||
| See the file LICENSE for details and copyright. | |||
| */ | |||
| #ifndef _XMALLOC_H | |||
| #define _XMALLOC_H 1 | |||
| void *xmalloc_impl(size_t size, const char *file, int line, const char *func); | |||
| void *xcalloc_impl(size_t nmemb, size_t size, const char *file, int line, | |||
| const char *func); | |||
| void xfree_impl(void *ptr, const char *file, int line, const char *func); | |||
| void *xrealloc_impl(void *ptr, size_t new_size, const char *file, int line, | |||
| const char *func); | |||
| int xmalloc_dump_leaks(void); | |||
| void xmalloc_configure(int fail_after); | |||
| #ifndef XMALLOC_INTERNAL | |||
| #ifdef MALLOC_DEBUGGING | |||
| /* Version 2.4 and later of GCC define a magical variable `__PRETTY_FUNCTION__' | |||
| which contains the name of the function currently being defined. | |||
| # define __XMALLOC_FUNCTION __PRETTY_FUNCTION__ | |||
| This is broken in G++ before version 2.6. | |||
| C9x has a similar variable called __func__, but prefer the GCC one since | |||
| it demangles C++ function names. */ | |||
| # ifdef __GNUC__ | |||
| # if __GNUC__ > 2 || (__GNUC__ == 2 \ | |||
| && __GNUC_MINOR__ >= (defined __cplusplus ? 6 : 4)) | |||
| # define __XMALLOC_FUNCTION __PRETTY_FUNCTION__ | |||
| # else | |||
| # define __XMALLOC_FUNCTION ((const char *) 0) | |||
| # endif | |||
| # else | |||
| # if defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L | |||
| # define __XMALLOC_FUNCTION __func__ | |||
| # else | |||
| # define __XMALLOC_FUNCTION ((const char *) 0) | |||
| # endif | |||
| # endif | |||
| #define xmalloc(size) xmalloc_impl(size, __FILE__, __LINE__, \ | |||
| __XMALLOC_FUNCTION) | |||
| #define xcalloc(nmemb, size) xcalloc_impl(nmemb, size, __FILE__, __LINE__, \ | |||
| __XMALLOC_FUNCTION) | |||
| #define xfree(ptr) xfree_impl(ptr, __FILE__, __LINE__, __XMALLOC_FUNCTION) | |||
| #define xrealloc(ptr, new_size) xrealloc_impl(ptr, new_size, __FILE__, \ | |||
| __LINE__, __XMALLOC_FUNCTION) | |||
| #undef malloc | |||
| #undef calloc | |||
| #undef free | |||
| #undef realloc | |||
| #define malloc USE_XMALLOC_INSTEAD_OF_MALLOC | |||
| #define calloc USE_XCALLOC_INSTEAD_OF_CALLOC | |||
| #define free USE_XFREE_INSTEAD_OF_FREE | |||
| #define realloc USE_XREALLOC_INSTEAD_OF_REALLOC | |||
| #else /* !MALLOC_DEBUGGING */ | |||
| #include <stdlib.h> | |||
| #define xmalloc(size) malloc(size) | |||
| #define xcalloc(nmemb, size) calloc(nmemb, size) | |||
| #define xfree(ptr) free(ptr) | |||
| #define xrealloc(ptr, new_size) realloc(ptr, new_size) | |||
| #endif /* !MALLOC_DEBUGGING */ | |||
| #endif /* !XMALLOC_INTERNAL */ | |||
| #endif /* _XMALLOC_H */ | |||
| /* EOF */ | |||
| @@ -0,0 +1,6 @@ | |||
| EXTRA_DIST = \ | |||
| ac_libtool_tags.m4 \ | |||
| ax_check_funcs_comp.m4 \ | |||
| ax_check_sign.m4 \ | |||
| ax_decl_wchar_max.m4 \ | |||
| vl_prog_cc_warnings.m4 | |||
| @@ -0,0 +1,359 @@ | |||
| # Makefile.in generated by automake 1.10.1 from Makefile.am. | |||
| # @configure_input@ | |||
| # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, | |||
| # 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. | |||
| # This Makefile.in is free software; the Free Software Foundation | |||
| # gives unlimited permission to copy and/or distribute it, | |||
| # with or without modifications, as long as this notice is preserved. | |||
| # This program is distributed in the hope that it will be useful, | |||
| # but WITHOUT ANY WARRANTY, to the extent permitted by law; without | |||
| # even the implied warranty of MERCHANTABILITY or FITNESS FOR A | |||
| # PARTICULAR PURPOSE. | |||
| @SET_MAKE@ | |||
| VPATH = @srcdir@ | |||
| pkgdatadir = $(datadir)/@PACKAGE@ | |||
| pkglibdir = $(libdir)/@PACKAGE@ | |||
| pkgincludedir = $(includedir)/@PACKAGE@ | |||
| am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd | |||
| install_sh_DATA = $(install_sh) -c -m 644 | |||
| install_sh_PROGRAM = $(install_sh) -c | |||
| install_sh_SCRIPT = $(install_sh) -c | |||
| INSTALL_HEADER = $(INSTALL_DATA) | |||
| transform = $(program_transform_name) | |||
| NORMAL_INSTALL = : | |||
| PRE_INSTALL = : | |||
| POST_INSTALL = : | |||
| NORMAL_UNINSTALL = : | |||
| PRE_UNINSTALL = : | |||
| POST_UNINSTALL = : | |||
| build_triplet = @build@ | |||
| host_triplet = @host@ | |||
| target_triplet = @target@ | |||
| subdir = m4 | |||
| DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in | |||
| ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 | |||
| am__aclocal_m4_deps = $(top_srcdir)/m4/ac_libtool_tags.m4 \ | |||
| $(top_srcdir)/m4/ax_check_funcs_comp.m4 \ | |||
| $(top_srcdir)/m4/ax_check_sign.m4 \ | |||
| $(top_srcdir)/m4/ax_decl_wchar_max.m4 \ | |||
| $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ | |||
| $(top_srcdir)/m4/intlmacosx.m4 $(top_srcdir)/m4/lib-ld.m4 \ | |||
| $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ | |||
| $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ | |||
| $(top_srcdir)/m4/progtest.m4 \ | |||
| $(top_srcdir)/m4/vl_prog_cc_warnings.m4 \ | |||
| $(top_srcdir)/configure.ac | |||
| am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ | |||
| $(ACLOCAL_M4) | |||
| mkinstalldirs = $(SHELL) $(top_srcdir)/utils/mkinstalldirs | |||
| CONFIG_HEADER = $(top_builddir)/config.h \ | |||
| $(top_builddir)/lib/tre-config.h | |||
| CONFIG_CLEAN_FILES = | |||
| SOURCES = | |||
| DIST_SOURCES = | |||
| DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) | |||
| ACLOCAL = @ACLOCAL@ | |||
| ALLOCA = @ALLOCA@ | |||
| AMTAR = @AMTAR@ | |||
| AR = @AR@ | |||
| AS = @AS@ | |||
| AUTOCONF = @AUTOCONF@ | |||
| AUTOHEADER = @AUTOHEADER@ | |||
| AUTOMAKE = @AUTOMAKE@ | |||
| AWK = @AWK@ | |||
| CC = @CC@ | |||
| CCDEPMODE = @CCDEPMODE@ | |||
| CFLAGS = @CFLAGS@ | |||
| CPP = @CPP@ | |||
| CPPFLAGS = @CPPFLAGS@ | |||
| CYGPATH_W = @CYGPATH_W@ | |||
| DEFS = @DEFS@ | |||
| DEPDIR = @DEPDIR@ | |||
| DLLTOOL = @DLLTOOL@ | |||
| DSYMUTIL = @DSYMUTIL@ | |||
| ECHO = @ECHO@ | |||
| ECHO_C = @ECHO_C@ | |||
| ECHO_N = @ECHO_N@ | |||
| ECHO_T = @ECHO_T@ | |||
| EGREP = @EGREP@ | |||
| EXEEXT = @EXEEXT@ | |||
| GETTEXT_MACRO_VERSION = @GETTEXT_MACRO_VERSION@ | |||
| GMSGFMT = @GMSGFMT@ | |||
| GMSGFMT_015 = @GMSGFMT_015@ | |||
| GREP = @GREP@ | |||
| INSTALL = @INSTALL@ | |||
| INSTALL_DATA = @INSTALL_DATA@ | |||
| INSTALL_PROGRAM = @INSTALL_PROGRAM@ | |||
| INSTALL_SCRIPT = @INSTALL_SCRIPT@ | |||
| INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ | |||
| INTLLIBS = @INTLLIBS@ | |||
| INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ | |||
| LDFLAGS = @LDFLAGS@ | |||
| LIBICONV = @LIBICONV@ | |||
| LIBINTL = @LIBINTL@ | |||
| LIBOBJS = @LIBOBJS@ | |||
| LIBS = @LIBS@ | |||
| LIBTOOL = @LIBTOOL@ | |||
| LN_S = @LN_S@ | |||
| LTLIBICONV = @LTLIBICONV@ | |||
| LTLIBINTL = @LTLIBINTL@ | |||
| LTLIBOBJS = @LTLIBOBJS@ | |||
| MAKEINFO = @MAKEINFO@ | |||
| MKDIR_P = @MKDIR_P@ | |||
| MSGFMT = @MSGFMT@ | |||
| MSGFMT_015 = @MSGFMT_015@ | |||
| MSGMERGE = @MSGMERGE@ | |||
| NMEDIT = @NMEDIT@ | |||
| OBJDUMP = @OBJDUMP@ | |||
| OBJEXT = @OBJEXT@ | |||
| PACKAGE = @PACKAGE@ | |||
| PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ | |||
| PACKAGE_NAME = @PACKAGE_NAME@ | |||
| PACKAGE_STRING = @PACKAGE_STRING@ | |||
| PACKAGE_TARNAME = @PACKAGE_TARNAME@ | |||
| PACKAGE_VERSION = @PACKAGE_VERSION@ | |||
| PATH_SEPARATOR = @PATH_SEPARATOR@ | |||
| POSUB = @POSUB@ | |||
| RANLIB = @RANLIB@ | |||
| SED = @SED@ | |||
| SET_MAKE = @SET_MAKE@ | |||
| SHELL = @SHELL@ | |||
| STRIP = @STRIP@ | |||
| TRE_VERSION = @TRE_VERSION@ | |||
| USE_NLS = @USE_NLS@ | |||
| VERSION = @VERSION@ | |||
| XGETTEXT = @XGETTEXT@ | |||
| XGETTEXT_015 = @XGETTEXT_015@ | |||
| XGETTEXT_EXTRA_OPTIONS = @XGETTEXT_EXTRA_OPTIONS@ | |||
| abs_builddir = @abs_builddir@ | |||
| abs_srcdir = @abs_srcdir@ | |||
| abs_top_builddir = @abs_top_builddir@ | |||
| abs_top_srcdir = @abs_top_srcdir@ | |||
| ac_ct_CC = @ac_ct_CC@ | |||
| am__include = @am__include@ | |||
| am__leading_dot = @am__leading_dot@ | |||
| am__quote = @am__quote@ | |||
| am__tar = @am__tar@ | |||
| am__untar = @am__untar@ | |||
| bindir = @bindir@ | |||
| build = @build@ | |||
| build_alias = @build_alias@ | |||
| build_cpu = @build_cpu@ | |||
| build_os = @build_os@ | |||
| build_vendor = @build_vendor@ | |||
| builddir = @builddir@ | |||
| datadir = @datadir@ | |||
| datarootdir = @datarootdir@ | |||
| docdir = @docdir@ | |||
| dvidir = @dvidir@ | |||
| exec_prefix = @exec_prefix@ | |||
| host = @host@ | |||
| host_alias = @host_alias@ | |||
| host_cpu = @host_cpu@ | |||
| host_os = @host_os@ | |||
| host_vendor = @host_vendor@ | |||
| htmldir = @htmldir@ | |||
| includedir = @includedir@ | |||
| infodir = @infodir@ | |||
| install_sh = @install_sh@ | |||
| libdir = @libdir@ | |||
| libexecdir = @libexecdir@ | |||
| localedir = @localedir@ | |||
| localstatedir = @localstatedir@ | |||
| mandir = @mandir@ | |||
| mkdir_p = @mkdir_p@ | |||
| oldincludedir = @oldincludedir@ | |||
| pdfdir = @pdfdir@ | |||
| prefix = @prefix@ | |||
| program_transform_name = @program_transform_name@ | |||
| psdir = @psdir@ | |||
| sbindir = @sbindir@ | |||
| sharedstatedir = @sharedstatedir@ | |||
| srcdir = @srcdir@ | |||
| sysconfdir = @sysconfdir@ | |||
| target = @target@ | |||
| target_alias = @target_alias@ | |||
| target_cpu = @target_cpu@ | |||
| target_os = @target_os@ | |||
| target_vendor = @target_vendor@ | |||
| top_builddir = @top_builddir@ | |||
| top_srcdir = @top_srcdir@ | |||
| EXTRA_DIST = \ | |||
| ac_libtool_tags.m4 \ | |||
| ax_check_funcs_comp.m4 \ | |||
| ax_check_sign.m4 \ | |||
| ax_decl_wchar_max.m4 \ | |||
| vl_prog_cc_warnings.m4 | |||
| all: all-am | |||
| .SUFFIXES: | |||
| $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) | |||
| @for dep in $?; do \ | |||
| case '$(am__configure_deps)' in \ | |||
| *$$dep*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ | |||
| && exit 0; \ | |||
| exit 1;; \ | |||
| esac; \ | |||
| done; \ | |||
| echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign m4/Makefile'; \ | |||
| cd $(top_srcdir) && \ | |||
| $(AUTOMAKE) --foreign m4/Makefile | |||
| .PRECIOUS: Makefile | |||
| Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status | |||
| @case '$?' in \ | |||
| *config.status*) \ | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ | |||
| *) \ | |||
| echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ | |||
| cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ | |||
| esac; | |||
| $(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(top_srcdir)/configure: $(am__configure_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| $(ACLOCAL_M4): $(am__aclocal_m4_deps) | |||
| cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh | |||
| mostlyclean-libtool: | |||
| -rm -f *.lo | |||
| clean-libtool: | |||
| -rm -rf .libs _libs | |||
| tags: TAGS | |||
| TAGS: | |||
| ctags: CTAGS | |||
| CTAGS: | |||
| distdir: $(DISTFILES) | |||
| @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ | |||
| list='$(DISTFILES)'; \ | |||
| dist_files=`for file in $$list; do echo $$file; done | \ | |||
| sed -e "s|^$$srcdirstrip/||;t" \ | |||
| -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ | |||
| case $$dist_files in \ | |||
| */*) $(MKDIR_P) `echo "$$dist_files" | \ | |||
| sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ | |||
| sort -u` ;; \ | |||
| esac; \ | |||
| for file in $$dist_files; do \ | |||
| if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ | |||
| if test -d $$d/$$file; then \ | |||
| dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ | |||
| if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ | |||
| cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ | |||
| fi; \ | |||
| cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ | |||
| else \ | |||
| test -f $(distdir)/$$file \ | |||
| || cp -p $$d/$$file $(distdir)/$$file \ | |||
| || exit 1; \ | |||
| fi; \ | |||
| done | |||
| check-am: all-am | |||
| check: check-am | |||
| all-am: Makefile | |||
| installdirs: | |||
| install: install-am | |||
| install-exec: install-exec-am | |||
| install-data: install-data-am | |||
| uninstall: uninstall-am | |||
| install-am: all-am | |||
| @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am | |||
| installcheck: installcheck-am | |||
| install-strip: | |||
| $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ | |||
| install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ | |||
| `test -z '$(STRIP)' || \ | |||
| echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install | |||
| mostlyclean-generic: | |||
| clean-generic: | |||
| distclean-generic: | |||
| -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) | |||
| maintainer-clean-generic: | |||
| @echo "This command is intended for maintainers to use" | |||
| @echo "it deletes files that may require special tools to rebuild." | |||
| clean: clean-am | |||
| clean-am: clean-generic clean-libtool mostlyclean-am | |||
| distclean: distclean-am | |||
| -rm -f Makefile | |||
| distclean-am: clean-am distclean-generic | |||
| dvi: dvi-am | |||
| dvi-am: | |||
| html: html-am | |||
| info: info-am | |||
| info-am: | |||
| install-data-am: | |||
| install-dvi: install-dvi-am | |||
| install-exec-am: | |||
| install-html: install-html-am | |||
| install-info: install-info-am | |||
| install-man: | |||
| install-pdf: install-pdf-am | |||
| install-ps: install-ps-am | |||
| installcheck-am: | |||
| maintainer-clean: maintainer-clean-am | |||
| -rm -f Makefile | |||
| maintainer-clean-am: distclean-am maintainer-clean-generic | |||
| mostlyclean: mostlyclean-am | |||
| mostlyclean-am: mostlyclean-generic mostlyclean-libtool | |||
| pdf: pdf-am | |||
| pdf-am: | |||
| ps: ps-am | |||
| ps-am: | |||
| uninstall-am: | |||
| .MAKE: install-am install-strip | |||
| .PHONY: all all-am check check-am clean clean-generic clean-libtool \ | |||
| distclean distclean-generic distclean-libtool distdir dvi \ | |||
| dvi-am html html-am info info-am install install-am \ | |||
| install-data install-data-am install-dvi install-dvi-am \ | |||
| install-exec install-exec-am install-html install-html-am \ | |||
| install-info install-info-am install-man install-pdf \ | |||
| install-pdf-am install-ps install-ps-am install-strip \ | |||
| installcheck installcheck-am installdirs maintainer-clean \ | |||
| maintainer-clean-generic mostlyclean mostlyclean-generic \ | |||
| mostlyclean-libtool pdf pdf-am ps ps-am uninstall uninstall-am | |||
| # Tell versions [3.59,3.63) of GNU make to not export all variables. | |||
| # Otherwise a system limit (for SysV at least) may be exceeded. | |||
| .NOEXPORT: | |||
| @@ -0,0 +1,55 @@ | |||
| # backported from libtool 1.6 by Paolo Bonzini | |||
| # When AC_LIBTOOL_TAGS is used, I redefine _LT_AC_TAGCONFIG | |||
| # to be more similar to the libtool 1.6 implementation, which | |||
| # uses an m4 loop and m4 case instead of a shell loop. This | |||
| # way the CXX/GCJ/F77/RC tests are not always expanded. | |||
| # AC_LIBTOOL_TAGS | |||
| # --------------- | |||
| # tags to enable | |||
| AC_DEFUN([AC_LIBTOOL_TAGS], | |||
| [m4_define([_LT_TAGS],[$1]) | |||
| m4_define([_LT_AC_TAGCONFIG], [ | |||
| if test -f "$ltmain"; then | |||
| if test ! -f "${ofile}"; then | |||
| AC_MSG_WARN([output file `$ofile' does not exist]) | |||
| fi | |||
| if test -z "$LTCC"; then | |||
| eval "`$SHELL ${ofile} --config | grep '^LTCC='`" | |||
| if test -z "$LTCC"; then | |||
| AC_MSG_WARN([output file `$ofile' does not look like a libtool script]) | |||
| else | |||
| AC_MSG_WARN([using `LTCC=$LTCC', extracted from `$ofile']) | |||
| fi | |||
| fi | |||
| AC_FOREACH([_LT_TAG], _LT_TAGS, | |||
| [m4_case(_LT_TAG, | |||
| [CXX], [ | |||
| if test -n "$CXX" && test "X$CXX" != "Xno"; then | |||
| AC_LIBTOOL_LANG_CXX_CONFIG | |||
| available_tags="$available_tags _LT_TAG" | |||
| fi], | |||
| [F77], [ | |||
| if test -n "$F77" && test "X$F77" != "Xno"; then | |||
| AC_LIBTOOL_LANG_F77_CONFIG | |||
| available_tags="$available_tags _LT_TAG" | |||
| fi], | |||
| [GCJ], [ | |||
| if test -n "$GCJ" && test "X$GCJ" != "Xno"; then | |||
| AC_LIBTOOL_LANG_GCJ_CONFIG | |||
| available_tags="$available_tags _LT_TAG" | |||
| fi], | |||
| [RC], [ | |||
| if test -n "$RC" && test "X$RC" != "Xno"; then | |||
| AC_LIBTOOL_LANG_RC_CONFIG | |||
| available_tags="$available_tags _LT_TAG" | |||
| fi], | |||
| [m4_errprintn(m4_location[: error: invalid tag name: ]"_LT_TAG") | |||
| m4_exit(1)]) | |||
| ]) | |||
| fi | |||
| ])dnl _LT_AC_TAG_CONFIG | |||
| ]) | |||
| @@ -0,0 +1,32 @@ | |||
| dnl Like AC_CHECK_FUNCS, but allows the function definition to be | |||
| dnl a macro. This allows for detection of functions which are renamed | |||
| dnl with macros to something other than the name we are testing with. | |||
| AC_DEFUN([AX_CHECK_FUNCS_COMP],[ | |||
| dnl This is magic to make autoheader pick up the config.h.in templates | |||
| dnl automatically. This uses macros which are probably not public | |||
| dnl (not documented anyway) but this works at least with Automake 2.59. | |||
| AC_FOREACH([AX_Func], [$1], | |||
| [AH_TEMPLATE(AS_TR_CPP(HAVE_[]AX_Func), | |||
| [Define to 1 if you have the `]AX_Func[' function or macro.])])dnl | |||
| for ax_func in $1; do | |||
| ax_fname=`echo $ax_func | sed "s/@<:@^a-zA-Z0-9_@:>@/_/g"` | |||
| ax_symbolname=`echo $ax_func | sed "s/@<:@^a-zA-Z0-9_@:>@/_/g" | tr "@<:@a-z@:>@" "@<:@A-Z@:>@"` | |||
| AC_CACHE_CHECK([for $ax_func], ax_cv_func_${ax_fname}, [ | |||
| AC_LINK_IFELSE( | |||
| [ AC_LANG_PROGRAM( | |||
| [$4 | |||
| void *foo = $ax_func; | |||
| ], | |||
| [ return foo != $ax_func; ])], | |||
| [ eval "ax_cv_func_${ax_fname}=\"yes\"" ], | |||
| [ eval "ax_cv_func_${ax_fname}=\"no\"" ])]) | |||
| if eval "test \"\${ax_cv_func_${ax_fname}}\" = \"yes\""; then | |||
| AC_DEFINE_UNQUOTED(HAVE_${ax_symbolname}, 1, | |||
| [Define to 1 if you have the $ax_func() function.]) | |||
| $2 | |||
| else | |||
| true | |||
| $3 | |||
| fi | |||
| done | |||
| ])dnl | |||
| @@ -0,0 +1,39 @@ | |||
| dnl @synopsis AX_CHECK_SIGN (TYPE, [ACTION-IF-SIGNED], [ACTION-IF-UNSIGNED], [INCLUDES]) | |||
| dnl | |||
| dnl Checks whether TYPE is signed or not. If no INCLUDES are specified, | |||
| dnl the default includes are used. If ACTION-IF-SIGNED is given, it is | |||
| dnl additional shell code to execute when the type is signed. If | |||
| dnl ACTION-IF-UNSIGNED is given, it is executed when the type is unsigned. | |||
| dnl | |||
| dnl This macro assumes that the type exists. Therefore the existence of | |||
| dnl the type should be checked before calling this macro. For example: | |||
| dnl | |||
| dnl AC_CHECK_HEADERS([wchar.h]) | |||
| dnl AC_CHECK_TYPE([wchar_t],,[ AC_MSG_ERROR([Type wchar_t not found.]) ]) | |||
| dnl AX_CHECK_SIGN([wchar_t], | |||
| dnl [ AC_DEFINE(WCHAR_T_SIGNED, 1, [Define if wchar_t is signed]) ], | |||
| dnl [ AC_DEFINE(WCHAR_T_UNSIGNED, 1, [Define if wchar_t is unsigned]) ], [ | |||
| dnl #ifdef HAVE_WCHAR_H | |||
| dnl #include <wchar.h> | |||
| dnl #endif | |||
| dnl ]) | |||
| dnl | |||
| dnl @version 1.1 | |||
| dnl @author Ville Laurikari <vl@iki.fi> | |||
| AC_DEFUN([AX_CHECK_SIGN], [ | |||
| typename=`echo $1 | sed "s/@<:@^a-zA-Z0-9_@:>@/_/g"` | |||
| AC_CACHE_CHECK([whether $1 is signed], ax_cv_decl_${typename}_signed, [ | |||
| AC_COMPILE_IFELSE( | |||
| [ AC_LANG_PROGRAM([$4], | |||
| [ int foo @<:@ 1 - 2 * !((($1) -1) < 0) @:>@ ])], | |||
| [ eval "ax_cv_decl_${typename}_signed=\"yes\"" ], | |||
| [ eval "ax_cv_decl_${typename}_signed=\"no\"" ])]) | |||
| symbolname=`echo $1 | sed "s/@<:@^a-zA-Z0-9_@:>@/_/g" | tr "@<:@a-z@:>@" "@<:@A-Z@:>@"` | |||
| if eval "test \"\${ax_cv_decl_${typename}_signed}\" = \"yes\""; then | |||
| true | |||
| $2 | |||
| elif eval "test \"\${ax_cv_decl_${typename}_signed}\" = \"no\""; then | |||
| true | |||
| $3 | |||
| fi | |||
| ])dnl | |||
| @@ -0,0 +1,38 @@ | |||
| dnl @synopsis AX_DECL_WCHAR_MAX | |||
| dnl | |||
| dnl Checks whether the system headers define WCHAR_MAX or not. If it is | |||
| dnl already defined, does nothing. Otherwise checks the size and signedness | |||
| dnl of `wchar_t', and defines WCHAR_MAX to the maximum value that can be | |||
| dnl stored in a variable of type `wchar_t'. | |||
| dnl | |||
| dnl @version 1.1 | |||
| dnl @author Ville Laurikari <vl@iki.fi> | |||
| dnl | |||
| AC_DEFUN([AX_DECL_WCHAR_MAX], [ | |||
| AC_CACHE_CHECK([whether WCHAR_MAX is defined], ax_cv_decl_wchar_max, [ | |||
| AC_COMPILE_IFELSE( | |||
| [AC_LANG_PROGRAM([ | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif | |||
| ], [WCHAR_MAX])], | |||
| [ax_cv_decl_wchar_max="yes"], | |||
| [ax_cv_decl_wchar_max="no"])]) | |||
| if test $ax_cv_decl_wchar_max = "no"; then | |||
| AX_CHECK_SIGN([wchar_t], | |||
| [ wc_signed="yes" | |||
| AC_DEFINE(WCHAR_T_SIGNED, 1, [Define if wchar_t is signed]) ], | |||
| [ wc_signed="no" | |||
| AC_DEFINE(WCHAR_T_UNSIGNED, 1, [Define if wchar_t is unsigned])], [ | |||
| #ifdef HAVE_WCHAR_H | |||
| #include <wchar.h> | |||
| #endif | |||
| ]) | |||
| if test "$wc_signed" = "yes"; then | |||
| AC_DEFINE(WCHAR_MAX, [(1L << (sizeof(wchar_t) * 8 - 1) - 1)], [ | |||
| Define to the maximum value of wchar_t if not already defined elsewhere]) | |||
| elif test "$wc_signed" = "no"; then | |||
| AC_DEFINE(WCHAR_MAX, [(1L << (sizeof(wchar_t) * 8) - 1)]) | |||
| fi | |||
| fi | |||
| ])dnl | |||
| @@ -0,0 +1,381 @@ | |||
| # gettext.m4 serial 60 (gettext-0.17) | |||
| dnl Copyright (C) 1995-2007 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl | |||
| dnl This file can can be used in projects which are not available under | |||
| dnl the GNU General Public License or the GNU Library General Public | |||
| dnl License but which still want to provide support for the GNU gettext | |||
| dnl functionality. | |||
| dnl Please note that the actual code of the GNU gettext library is covered | |||
| dnl by the GNU Library General Public License, and the rest of the GNU | |||
| dnl gettext package package is covered by the GNU General Public License. | |||
| dnl They are *not* in the public domain. | |||
| dnl Authors: | |||
| dnl Ulrich Drepper <drepper@cygnus.com>, 1995-2000. | |||
| dnl Bruno Haible <haible@clisp.cons.org>, 2000-2006. | |||
| dnl Macro to add for using GNU gettext. | |||
| dnl Usage: AM_GNU_GETTEXT([INTLSYMBOL], [NEEDSYMBOL], [INTLDIR]). | |||
| dnl INTLSYMBOL can be one of 'external', 'no-libtool', 'use-libtool'. The | |||
| dnl default (if it is not specified or empty) is 'no-libtool'. | |||
| dnl INTLSYMBOL should be 'external' for packages with no intl directory, | |||
| dnl and 'no-libtool' or 'use-libtool' for packages with an intl directory. | |||
| dnl If INTLSYMBOL is 'use-libtool', then a libtool library | |||
| dnl $(top_builddir)/intl/libintl.la will be created (shared and/or static, | |||
| dnl depending on --{enable,disable}-{shared,static} and on the presence of | |||
| dnl AM-DISABLE-SHARED). If INTLSYMBOL is 'no-libtool', a static library | |||
| dnl $(top_builddir)/intl/libintl.a will be created. | |||
| dnl If NEEDSYMBOL is specified and is 'need-ngettext', then GNU gettext | |||
| dnl implementations (in libc or libintl) without the ngettext() function | |||
| dnl will be ignored. If NEEDSYMBOL is specified and is | |||
| dnl 'need-formatstring-macros', then GNU gettext implementations that don't | |||
| dnl support the ISO C 99 <inttypes.h> formatstring macros will be ignored. | |||
| dnl INTLDIR is used to find the intl libraries. If empty, | |||
| dnl the value `$(top_builddir)/intl/' is used. | |||
| dnl | |||
| dnl The result of the configuration is one of three cases: | |||
| dnl 1) GNU gettext, as included in the intl subdirectory, will be compiled | |||
| dnl and used. | |||
| dnl Catalog format: GNU --> install in $(datadir) | |||
| dnl Catalog extension: .mo after installation, .gmo in source tree | |||
| dnl 2) GNU gettext has been found in the system's C library. | |||
| dnl Catalog format: GNU --> install in $(datadir) | |||
| dnl Catalog extension: .mo after installation, .gmo in source tree | |||
| dnl 3) No internationalization, always use English msgid. | |||
| dnl Catalog format: none | |||
| dnl Catalog extension: none | |||
| dnl If INTLSYMBOL is 'external', only cases 2 and 3 can occur. | |||
| dnl The use of .gmo is historical (it was needed to avoid overwriting the | |||
| dnl GNU format catalogs when building on a platform with an X/Open gettext), | |||
| dnl but we keep it in order not to force irrelevant filename changes on the | |||
| dnl maintainers. | |||
| dnl | |||
| AC_DEFUN([AM_GNU_GETTEXT], | |||
| [ | |||
| dnl Argument checking. | |||
| ifelse([$1], [], , [ifelse([$1], [external], , [ifelse([$1], [no-libtool], , [ifelse([$1], [use-libtool], , | |||
| [errprint([ERROR: invalid first argument to AM_GNU_GETTEXT | |||
| ])])])])]) | |||
| ifelse([$2], [], , [ifelse([$2], [need-ngettext], , [ifelse([$2], [need-formatstring-macros], , | |||
| [errprint([ERROR: invalid second argument to AM_GNU_GETTEXT | |||
| ])])])]) | |||
| define([gt_included_intl], | |||
| ifelse([$1], [external], | |||
| ifdef([AM_GNU_GETTEXT_][INTL_SUBDIR], [yes], [no]), | |||
| [yes])) | |||
| define([gt_libtool_suffix_prefix], ifelse([$1], [use-libtool], [l], [])) | |||
| gt_NEEDS_INIT | |||
| AM_GNU_GETTEXT_NEED([$2]) | |||
| AC_REQUIRE([AM_PO_SUBDIRS])dnl | |||
| ifelse(gt_included_intl, yes, [ | |||
| AC_REQUIRE([AM_INTL_SUBDIR])dnl | |||
| ]) | |||
| dnl Prerequisites of AC_LIB_LINKFLAGS_BODY. | |||
| AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) | |||
| AC_REQUIRE([AC_LIB_RPATH]) | |||
| dnl Sometimes libintl requires libiconv, so first search for libiconv. | |||
| dnl Ideally we would do this search only after the | |||
| dnl if test "$USE_NLS" = "yes"; then | |||
| dnl if { eval "gt_val=\$$gt_func_gnugettext_libc"; test "$gt_val" != "yes"; }; then | |||
| dnl tests. But if configure.in invokes AM_ICONV after AM_GNU_GETTEXT | |||
| dnl the configure script would need to contain the same shell code | |||
| dnl again, outside any 'if'. There are two solutions: | |||
| dnl - Invoke AM_ICONV_LINKFLAGS_BODY here, outside any 'if'. | |||
| dnl - Control the expansions in more detail using AC_PROVIDE_IFELSE. | |||
| dnl Since AC_PROVIDE_IFELSE is only in autoconf >= 2.52 and not | |||
| dnl documented, we avoid it. | |||
| ifelse(gt_included_intl, yes, , [ | |||
| AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY]) | |||
| ]) | |||
| dnl Sometimes, on MacOS X, libintl requires linking with CoreFoundation. | |||
| gt_INTL_MACOSX | |||
| dnl Set USE_NLS. | |||
| AC_REQUIRE([AM_NLS]) | |||
| ifelse(gt_included_intl, yes, [ | |||
| BUILD_INCLUDED_LIBINTL=no | |||
| USE_INCLUDED_LIBINTL=no | |||
| ]) | |||
| LIBINTL= | |||
| LTLIBINTL= | |||
| POSUB= | |||
| dnl Add a version number to the cache macros. | |||
| case " $gt_needs " in | |||
| *" need-formatstring-macros "*) gt_api_version=3 ;; | |||
| *" need-ngettext "*) gt_api_version=2 ;; | |||
| *) gt_api_version=1 ;; | |||
| esac | |||
| gt_func_gnugettext_libc="gt_cv_func_gnugettext${gt_api_version}_libc" | |||
| gt_func_gnugettext_libintl="gt_cv_func_gnugettext${gt_api_version}_libintl" | |||
| dnl If we use NLS figure out what method | |||
| if test "$USE_NLS" = "yes"; then | |||
| gt_use_preinstalled_gnugettext=no | |||
| ifelse(gt_included_intl, yes, [ | |||
| AC_MSG_CHECKING([whether included gettext is requested]) | |||
| AC_ARG_WITH(included-gettext, | |||
| [ --with-included-gettext use the GNU gettext library included here], | |||
| nls_cv_force_use_gnu_gettext=$withval, | |||
| nls_cv_force_use_gnu_gettext=no) | |||
| AC_MSG_RESULT($nls_cv_force_use_gnu_gettext) | |||
| nls_cv_use_gnu_gettext="$nls_cv_force_use_gnu_gettext" | |||
| if test "$nls_cv_force_use_gnu_gettext" != "yes"; then | |||
| ]) | |||
| dnl User does not insist on using GNU NLS library. Figure out what | |||
| dnl to use. If GNU gettext is available we use this. Else we have | |||
| dnl to fall back to GNU NLS library. | |||
| if test $gt_api_version -ge 3; then | |||
| gt_revision_test_code=' | |||
| #ifndef __GNU_GETTEXT_SUPPORTED_REVISION | |||
| #define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1) | |||
| #endif | |||
| changequote(,)dnl | |||
| typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1]; | |||
| changequote([,])dnl | |||
| ' | |||
| else | |||
| gt_revision_test_code= | |||
| fi | |||
| if test $gt_api_version -ge 2; then | |||
| gt_expression_test_code=' + * ngettext ("", "", 0)' | |||
| else | |||
| gt_expression_test_code= | |||
| fi | |||
| AC_CACHE_CHECK([for GNU gettext in libc], [$gt_func_gnugettext_libc], | |||
| [AC_TRY_LINK([#include <libintl.h> | |||
| $gt_revision_test_code | |||
| extern int _nl_msg_cat_cntr; | |||
| extern int *_nl_domain_bindings;], | |||
| [bindtextdomain ("", ""); | |||
| return * gettext ("")$gt_expression_test_code + _nl_msg_cat_cntr + *_nl_domain_bindings], | |||
| [eval "$gt_func_gnugettext_libc=yes"], | |||
| [eval "$gt_func_gnugettext_libc=no"])]) | |||
| if { eval "gt_val=\$$gt_func_gnugettext_libc"; test "$gt_val" != "yes"; }; then | |||
| dnl Sometimes libintl requires libiconv, so first search for libiconv. | |||
| ifelse(gt_included_intl, yes, , [ | |||
| AM_ICONV_LINK | |||
| ]) | |||
| dnl Search for libintl and define LIBINTL, LTLIBINTL and INCINTL | |||
| dnl accordingly. Don't use AC_LIB_LINKFLAGS_BODY([intl],[iconv]) | |||
| dnl because that would add "-liconv" to LIBINTL and LTLIBINTL | |||
| dnl even if libiconv doesn't exist. | |||
| AC_LIB_LINKFLAGS_BODY([intl]) | |||
| AC_CACHE_CHECK([for GNU gettext in libintl], | |||
| [$gt_func_gnugettext_libintl], | |||
| [gt_save_CPPFLAGS="$CPPFLAGS" | |||
| CPPFLAGS="$CPPFLAGS $INCINTL" | |||
| gt_save_LIBS="$LIBS" | |||
| LIBS="$LIBS $LIBINTL" | |||
| dnl Now see whether libintl exists and does not depend on libiconv. | |||
| AC_TRY_LINK([#include <libintl.h> | |||
| $gt_revision_test_code | |||
| extern int _nl_msg_cat_cntr; | |||
| extern | |||
| #ifdef __cplusplus | |||
| "C" | |||
| #endif | |||
| const char *_nl_expand_alias (const char *);], | |||
| [bindtextdomain ("", ""); | |||
| return * gettext ("")$gt_expression_test_code + _nl_msg_cat_cntr + *_nl_expand_alias ("")], | |||
| [eval "$gt_func_gnugettext_libintl=yes"], | |||
| [eval "$gt_func_gnugettext_libintl=no"]) | |||
| dnl Now see whether libintl exists and depends on libiconv. | |||
| if { eval "gt_val=\$$gt_func_gnugettext_libintl"; test "$gt_val" != yes; } && test -n "$LIBICONV"; then | |||
| LIBS="$LIBS $LIBICONV" | |||
| AC_TRY_LINK([#include <libintl.h> | |||
| $gt_revision_test_code | |||
| extern int _nl_msg_cat_cntr; | |||
| extern | |||
| #ifdef __cplusplus | |||
| "C" | |||
| #endif | |||
| const char *_nl_expand_alias (const char *);], | |||
| [bindtextdomain ("", ""); | |||
| return * gettext ("")$gt_expression_test_code + _nl_msg_cat_cntr + *_nl_expand_alias ("")], | |||
| [LIBINTL="$LIBINTL $LIBICONV" | |||
| LTLIBINTL="$LTLIBINTL $LTLIBICONV" | |||
| eval "$gt_func_gnugettext_libintl=yes" | |||
| ]) | |||
| fi | |||
| CPPFLAGS="$gt_save_CPPFLAGS" | |||
| LIBS="$gt_save_LIBS"]) | |||
| fi | |||
| dnl If an already present or preinstalled GNU gettext() is found, | |||
| dnl use it. But if this macro is used in GNU gettext, and GNU | |||
| dnl gettext is already preinstalled in libintl, we update this | |||
| dnl libintl. (Cf. the install rule in intl/Makefile.in.) | |||
| if { eval "gt_val=\$$gt_func_gnugettext_libc"; test "$gt_val" = "yes"; } \ | |||
| || { { eval "gt_val=\$$gt_func_gnugettext_libintl"; test "$gt_val" = "yes"; } \ | |||
| && test "$PACKAGE" != gettext-runtime \ | |||
| && test "$PACKAGE" != gettext-tools; }; then | |||
| gt_use_preinstalled_gnugettext=yes | |||
| else | |||
| dnl Reset the values set by searching for libintl. | |||
| LIBINTL= | |||
| LTLIBINTL= | |||
| INCINTL= | |||
| fi | |||
| ifelse(gt_included_intl, yes, [ | |||
| if test "$gt_use_preinstalled_gnugettext" != "yes"; then | |||
| dnl GNU gettext is not found in the C library. | |||
| dnl Fall back on included GNU gettext library. | |||
| nls_cv_use_gnu_gettext=yes | |||
| fi | |||
| fi | |||
| if test "$nls_cv_use_gnu_gettext" = "yes"; then | |||
| dnl Mark actions used to generate GNU NLS library. | |||
| BUILD_INCLUDED_LIBINTL=yes | |||
| USE_INCLUDED_LIBINTL=yes | |||
| LIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LIBICONV $LIBTHREAD" | |||
| LTLIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LTLIBICONV $LTLIBTHREAD" | |||
| LIBS=`echo " $LIBS " | sed -e 's/ -lintl / /' -e 's/^ //' -e 's/ $//'` | |||
| fi | |||
| CATOBJEXT= | |||
| if test "$gt_use_preinstalled_gnugettext" = "yes" \ | |||
| || test "$nls_cv_use_gnu_gettext" = "yes"; then | |||
| dnl Mark actions to use GNU gettext tools. | |||
| CATOBJEXT=.gmo | |||
| fi | |||
| ]) | |||
| if test -n "$INTL_MACOSX_LIBS"; then | |||
| if test "$gt_use_preinstalled_gnugettext" = "yes" \ | |||
| || test "$nls_cv_use_gnu_gettext" = "yes"; then | |||
| dnl Some extra flags are needed during linking. | |||
| LIBINTL="$LIBINTL $INTL_MACOSX_LIBS" | |||
| LTLIBINTL="$LTLIBINTL $INTL_MACOSX_LIBS" | |||
| fi | |||
| fi | |||
| if test "$gt_use_preinstalled_gnugettext" = "yes" \ | |||
| || test "$nls_cv_use_gnu_gettext" = "yes"; then | |||
| AC_DEFINE(ENABLE_NLS, 1, | |||
| [Define to 1 if translation of program messages to the user's native language | |||
| is requested.]) | |||
| else | |||
| USE_NLS=no | |||
| fi | |||
| fi | |||
| AC_MSG_CHECKING([whether to use NLS]) | |||
| AC_MSG_RESULT([$USE_NLS]) | |||
| if test "$USE_NLS" = "yes"; then | |||
| AC_MSG_CHECKING([where the gettext function comes from]) | |||
| if test "$gt_use_preinstalled_gnugettext" = "yes"; then | |||
| if { eval "gt_val=\$$gt_func_gnugettext_libintl"; test "$gt_val" = "yes"; }; then | |||
| gt_source="external libintl" | |||
| else | |||
| gt_source="libc" | |||
| fi | |||
| else | |||
| gt_source="included intl directory" | |||
| fi | |||
| AC_MSG_RESULT([$gt_source]) | |||
| fi | |||
| if test "$USE_NLS" = "yes"; then | |||
| if test "$gt_use_preinstalled_gnugettext" = "yes"; then | |||
| if { eval "gt_val=\$$gt_func_gnugettext_libintl"; test "$gt_val" = "yes"; }; then | |||
| AC_MSG_CHECKING([how to link with libintl]) | |||
| AC_MSG_RESULT([$LIBINTL]) | |||
| AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCINTL]) | |||
| fi | |||
| dnl For backward compatibility. Some packages may be using this. | |||
| AC_DEFINE(HAVE_GETTEXT, 1, | |||
| [Define if the GNU gettext() function is already present or preinstalled.]) | |||
| AC_DEFINE(HAVE_DCGETTEXT, 1, | |||
| [Define if the GNU dcgettext() function is already present or preinstalled.]) | |||
| fi | |||
| dnl We need to process the po/ directory. | |||
| POSUB=po | |||
| fi | |||
| ifelse(gt_included_intl, yes, [ | |||
| dnl If this is used in GNU gettext we have to set BUILD_INCLUDED_LIBINTL | |||
| dnl to 'yes' because some of the testsuite requires it. | |||
| if test "$PACKAGE" = gettext-runtime || test "$PACKAGE" = gettext-tools; then | |||
| BUILD_INCLUDED_LIBINTL=yes | |||
| fi | |||
| dnl Make all variables we use known to autoconf. | |||
| AC_SUBST(BUILD_INCLUDED_LIBINTL) | |||
| AC_SUBST(USE_INCLUDED_LIBINTL) | |||
| AC_SUBST(CATOBJEXT) | |||
| dnl For backward compatibility. Some configure.ins may be using this. | |||
| nls_cv_header_intl= | |||
| nls_cv_header_libgt= | |||
| dnl For backward compatibility. Some Makefiles may be using this. | |||
| DATADIRNAME=share | |||
| AC_SUBST(DATADIRNAME) | |||
| dnl For backward compatibility. Some Makefiles may be using this. | |||
| INSTOBJEXT=.mo | |||
| AC_SUBST(INSTOBJEXT) | |||
| dnl For backward compatibility. Some Makefiles may be using this. | |||
| GENCAT=gencat | |||
| AC_SUBST(GENCAT) | |||
| dnl For backward compatibility. Some Makefiles may be using this. | |||
| INTLOBJS= | |||
| if test "$USE_INCLUDED_LIBINTL" = yes; then | |||
| INTLOBJS="\$(GETTOBJS)" | |||
| fi | |||
| AC_SUBST(INTLOBJS) | |||
| dnl Enable libtool support if the surrounding package wishes it. | |||
| INTL_LIBTOOL_SUFFIX_PREFIX=gt_libtool_suffix_prefix | |||
| AC_SUBST(INTL_LIBTOOL_SUFFIX_PREFIX) | |||
| ]) | |||
| dnl For backward compatibility. Some Makefiles may be using this. | |||
| INTLLIBS="$LIBINTL" | |||
| AC_SUBST(INTLLIBS) | |||
| dnl Make all documented variables known to autoconf. | |||
| AC_SUBST(LIBINTL) | |||
| AC_SUBST(LTLIBINTL) | |||
| AC_SUBST(POSUB) | |||
| ]) | |||
| dnl gt_NEEDS_INIT ensures that the gt_needs variable is initialized. | |||
| m4_define([gt_NEEDS_INIT], | |||
| [ | |||
| m4_divert_text([DEFAULTS], [gt_needs=]) | |||
| m4_define([gt_NEEDS_INIT], []) | |||
| ]) | |||
| dnl Usage: AM_GNU_GETTEXT_NEED([NEEDSYMBOL]) | |||
| AC_DEFUN([AM_GNU_GETTEXT_NEED], | |||
| [ | |||
| m4_divert_text([INIT_PREPARE], [gt_needs="$gt_needs $1"]) | |||
| ]) | |||
| dnl Usage: AM_GNU_GETTEXT_VERSION([gettext-version]) | |||
| AC_DEFUN([AM_GNU_GETTEXT_VERSION], []) | |||
| @@ -0,0 +1,180 @@ | |||
| # iconv.m4 serial AM6 (gettext-0.17) | |||
| dnl Copyright (C) 2000-2002, 2007 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl From Bruno Haible. | |||
| AC_DEFUN([AM_ICONV_LINKFLAGS_BODY], | |||
| [ | |||
| dnl Prerequisites of AC_LIB_LINKFLAGS_BODY. | |||
| AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) | |||
| AC_REQUIRE([AC_LIB_RPATH]) | |||
| dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV | |||
| dnl accordingly. | |||
| AC_LIB_LINKFLAGS_BODY([iconv]) | |||
| ]) | |||
| AC_DEFUN([AM_ICONV_LINK], | |||
| [ | |||
| dnl Some systems have iconv in libc, some have it in libiconv (OSF/1 and | |||
| dnl those with the standalone portable GNU libiconv installed). | |||
| AC_REQUIRE([AC_CANONICAL_HOST]) dnl for cross-compiles | |||
| dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV | |||
| dnl accordingly. | |||
| AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY]) | |||
| dnl Add $INCICONV to CPPFLAGS before performing the following checks, | |||
| dnl because if the user has installed libiconv and not disabled its use | |||
| dnl via --without-libiconv-prefix, he wants to use it. The first | |||
| dnl AC_TRY_LINK will then fail, the second AC_TRY_LINK will succeed. | |||
| am_save_CPPFLAGS="$CPPFLAGS" | |||
| AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCICONV]) | |||
| AC_CACHE_CHECK([for iconv], am_cv_func_iconv, [ | |||
| am_cv_func_iconv="no, consider installing GNU libiconv" | |||
| am_cv_lib_iconv=no | |||
| AC_TRY_LINK([#include <stdlib.h> | |||
| #include <iconv.h>], | |||
| [iconv_t cd = iconv_open("",""); | |||
| iconv(cd,NULL,NULL,NULL,NULL); | |||
| iconv_close(cd);], | |||
| am_cv_func_iconv=yes) | |||
| if test "$am_cv_func_iconv" != yes; then | |||
| am_save_LIBS="$LIBS" | |||
| LIBS="$LIBS $LIBICONV" | |||
| AC_TRY_LINK([#include <stdlib.h> | |||
| #include <iconv.h>], | |||
| [iconv_t cd = iconv_open("",""); | |||
| iconv(cd,NULL,NULL,NULL,NULL); | |||
| iconv_close(cd);], | |||
| am_cv_lib_iconv=yes | |||
| am_cv_func_iconv=yes) | |||
| LIBS="$am_save_LIBS" | |||
| fi | |||
| ]) | |||
| if test "$am_cv_func_iconv" = yes; then | |||
| AC_CACHE_CHECK([for working iconv], am_cv_func_iconv_works, [ | |||
| dnl This tests against bugs in AIX 5.1 and HP-UX 11.11. | |||
| am_save_LIBS="$LIBS" | |||
| if test $am_cv_lib_iconv = yes; then | |||
| LIBS="$LIBS $LIBICONV" | |||
| fi | |||
| AC_TRY_RUN([ | |||
| #include <iconv.h> | |||
| #include <string.h> | |||
| int main () | |||
| { | |||
| /* Test against AIX 5.1 bug: Failures are not distinguishable from successful | |||
| returns. */ | |||
| { | |||
| iconv_t cd_utf8_to_88591 = iconv_open ("ISO8859-1", "UTF-8"); | |||
| if (cd_utf8_to_88591 != (iconv_t)(-1)) | |||
| { | |||
| static const char input[] = "\342\202\254"; /* EURO SIGN */ | |||
| char buf[10]; | |||
| const char *inptr = input; | |||
| size_t inbytesleft = strlen (input); | |||
| char *outptr = buf; | |||
| size_t outbytesleft = sizeof (buf); | |||
| size_t res = iconv (cd_utf8_to_88591, | |||
| (char **) &inptr, &inbytesleft, | |||
| &outptr, &outbytesleft); | |||
| if (res == 0) | |||
| return 1; | |||
| } | |||
| } | |||
| #if 0 /* This bug could be worked around by the caller. */ | |||
| /* Test against HP-UX 11.11 bug: Positive return value instead of 0. */ | |||
| { | |||
| iconv_t cd_88591_to_utf8 = iconv_open ("utf8", "iso88591"); | |||
| if (cd_88591_to_utf8 != (iconv_t)(-1)) | |||
| { | |||
| static const char input[] = "\304rger mit b\366sen B\374bchen ohne Augenma\337"; | |||
| char buf[50]; | |||
| const char *inptr = input; | |||
| size_t inbytesleft = strlen (input); | |||
| char *outptr = buf; | |||
| size_t outbytesleft = sizeof (buf); | |||
| size_t res = iconv (cd_88591_to_utf8, | |||
| (char **) &inptr, &inbytesleft, | |||
| &outptr, &outbytesleft); | |||
| if ((int)res > 0) | |||
| return 1; | |||
| } | |||
| } | |||
| #endif | |||
| /* Test against HP-UX 11.11 bug: No converter from EUC-JP to UTF-8 is | |||
| provided. */ | |||
| if (/* Try standardized names. */ | |||
| iconv_open ("UTF-8", "EUC-JP") == (iconv_t)(-1) | |||
| /* Try IRIX, OSF/1 names. */ | |||
| && iconv_open ("UTF-8", "eucJP") == (iconv_t)(-1) | |||
| /* Try AIX names. */ | |||
| && iconv_open ("UTF-8", "IBM-eucJP") == (iconv_t)(-1) | |||
| /* Try HP-UX names. */ | |||
| && iconv_open ("utf8", "eucJP") == (iconv_t)(-1)) | |||
| return 1; | |||
| return 0; | |||
| }], [am_cv_func_iconv_works=yes], [am_cv_func_iconv_works=no], | |||
| [case "$host_os" in | |||
| aix* | hpux*) am_cv_func_iconv_works="guessing no" ;; | |||
| *) am_cv_func_iconv_works="guessing yes" ;; | |||
| esac]) | |||
| LIBS="$am_save_LIBS" | |||
| ]) | |||
| case "$am_cv_func_iconv_works" in | |||
| *no) am_func_iconv=no am_cv_lib_iconv=no ;; | |||
| *) am_func_iconv=yes ;; | |||
| esac | |||
| else | |||
| am_func_iconv=no am_cv_lib_iconv=no | |||
| fi | |||
| if test "$am_func_iconv" = yes; then | |||
| AC_DEFINE(HAVE_ICONV, 1, | |||
| [Define if you have the iconv() function and it works.]) | |||
| fi | |||
| if test "$am_cv_lib_iconv" = yes; then | |||
| AC_MSG_CHECKING([how to link with libiconv]) | |||
| AC_MSG_RESULT([$LIBICONV]) | |||
| else | |||
| dnl If $LIBICONV didn't lead to a usable library, we don't need $INCICONV | |||
| dnl either. | |||
| CPPFLAGS="$am_save_CPPFLAGS" | |||
| LIBICONV= | |||
| LTLIBICONV= | |||
| fi | |||
| AC_SUBST(LIBICONV) | |||
| AC_SUBST(LTLIBICONV) | |||
| ]) | |||
| AC_DEFUN([AM_ICONV], | |||
| [ | |||
| AM_ICONV_LINK | |||
| if test "$am_cv_func_iconv" = yes; then | |||
| AC_MSG_CHECKING([for iconv declaration]) | |||
| AC_CACHE_VAL(am_cv_proto_iconv, [ | |||
| AC_TRY_COMPILE([ | |||
| #include <stdlib.h> | |||
| #include <iconv.h> | |||
| extern | |||
| #ifdef __cplusplus | |||
| "C" | |||
| #endif | |||
| #if defined(__STDC__) || defined(__cplusplus) | |||
| size_t iconv (iconv_t cd, char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft); | |||
| #else | |||
| size_t iconv(); | |||
| #endif | |||
| ], [], am_cv_proto_iconv_arg1="", am_cv_proto_iconv_arg1="const") | |||
| am_cv_proto_iconv="extern size_t iconv (iconv_t cd, $am_cv_proto_iconv_arg1 char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft);"]) | |||
| am_cv_proto_iconv=`echo "[$]am_cv_proto_iconv" | tr -s ' ' | sed -e 's/( /(/'` | |||
| AC_MSG_RESULT([$]{ac_t:- | |||
| }[$]am_cv_proto_iconv) | |||
| AC_DEFINE_UNQUOTED(ICONV_CONST, $am_cv_proto_iconv_arg1, | |||
| [Define as const if the declaration of iconv() needs const.]) | |||
| fi | |||
| ]) | |||
| @@ -0,0 +1,51 @@ | |||
| # intlmacosx.m4 serial 1 (gettext-0.17) | |||
| dnl Copyright (C) 2004-2007 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl | |||
| dnl This file can can be used in projects which are not available under | |||
| dnl the GNU General Public License or the GNU Library General Public | |||
| dnl License but which still want to provide support for the GNU gettext | |||
| dnl functionality. | |||
| dnl Please note that the actual code of the GNU gettext library is covered | |||
| dnl by the GNU Library General Public License, and the rest of the GNU | |||
| dnl gettext package package is covered by the GNU General Public License. | |||
| dnl They are *not* in the public domain. | |||
| dnl Checks for special options needed on MacOS X. | |||
| dnl Defines INTL_MACOSX_LIBS. | |||
| AC_DEFUN([gt_INTL_MACOSX], | |||
| [ | |||
| dnl Check for API introduced in MacOS X 10.2. | |||
| AC_CACHE_CHECK([for CFPreferencesCopyAppValue], | |||
| gt_cv_func_CFPreferencesCopyAppValue, | |||
| [gt_save_LIBS="$LIBS" | |||
| LIBS="$LIBS -Wl,-framework -Wl,CoreFoundation" | |||
| AC_TRY_LINK([#include <CoreFoundation/CFPreferences.h>], | |||
| [CFPreferencesCopyAppValue(NULL, NULL)], | |||
| [gt_cv_func_CFPreferencesCopyAppValue=yes], | |||
| [gt_cv_func_CFPreferencesCopyAppValue=no]) | |||
| LIBS="$gt_save_LIBS"]) | |||
| if test $gt_cv_func_CFPreferencesCopyAppValue = yes; then | |||
| AC_DEFINE([HAVE_CFPREFERENCESCOPYAPPVALUE], 1, | |||
| [Define to 1 if you have the MacOS X function CFPreferencesCopyAppValue in the CoreFoundation framework.]) | |||
| fi | |||
| dnl Check for API introduced in MacOS X 10.3. | |||
| AC_CACHE_CHECK([for CFLocaleCopyCurrent], gt_cv_func_CFLocaleCopyCurrent, | |||
| [gt_save_LIBS="$LIBS" | |||
| LIBS="$LIBS -Wl,-framework -Wl,CoreFoundation" | |||
| AC_TRY_LINK([#include <CoreFoundation/CFLocale.h>], [CFLocaleCopyCurrent();], | |||
| [gt_cv_func_CFLocaleCopyCurrent=yes], | |||
| [gt_cv_func_CFLocaleCopyCurrent=no]) | |||
| LIBS="$gt_save_LIBS"]) | |||
| if test $gt_cv_func_CFLocaleCopyCurrent = yes; then | |||
| AC_DEFINE([HAVE_CFLOCALECOPYCURRENT], 1, | |||
| [Define to 1 if you have the MacOS X function CFLocaleCopyCurrent in the CoreFoundation framework.]) | |||
| fi | |||
| INTL_MACOSX_LIBS= | |||
| if test $gt_cv_func_CFPreferencesCopyAppValue = yes || test $gt_cv_func_CFLocaleCopyCurrent = yes; then | |||
| INTL_MACOSX_LIBS="-Wl,-framework -Wl,CoreFoundation" | |||
| fi | |||
| AC_SUBST([INTL_MACOSX_LIBS]) | |||
| ]) | |||
| @@ -0,0 +1,110 @@ | |||
| # lib-ld.m4 serial 3 (gettext-0.13) | |||
| dnl Copyright (C) 1996-2003 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl Subroutines of libtool.m4, | |||
| dnl with replacements s/AC_/AC_LIB/ and s/lt_cv/acl_cv/ to avoid collision | |||
| dnl with libtool.m4. | |||
| dnl From libtool-1.4. Sets the variable with_gnu_ld to yes or no. | |||
| AC_DEFUN([AC_LIB_PROG_LD_GNU], | |||
| [AC_CACHE_CHECK([if the linker ($LD) is GNU ld], acl_cv_prog_gnu_ld, | |||
| [# I'd rather use --version here, but apparently some GNU ld's only accept -v. | |||
| case `$LD -v 2>&1 </dev/null` in | |||
| *GNU* | *'with BFD'*) | |||
| acl_cv_prog_gnu_ld=yes ;; | |||
| *) | |||
| acl_cv_prog_gnu_ld=no ;; | |||
| esac]) | |||
| with_gnu_ld=$acl_cv_prog_gnu_ld | |||
| ]) | |||
| dnl From libtool-1.4. Sets the variable LD. | |||
| AC_DEFUN([AC_LIB_PROG_LD], | |||
| [AC_ARG_WITH(gnu-ld, | |||
| [ --with-gnu-ld assume the C compiler uses GNU ld [default=no]], | |||
| test "$withval" = no || with_gnu_ld=yes, with_gnu_ld=no) | |||
| AC_REQUIRE([AC_PROG_CC])dnl | |||
| AC_REQUIRE([AC_CANONICAL_HOST])dnl | |||
| # Prepare PATH_SEPARATOR. | |||
| # The user is always right. | |||
| if test "${PATH_SEPARATOR+set}" != set; then | |||
| echo "#! /bin/sh" >conf$$.sh | |||
| echo "exit 0" >>conf$$.sh | |||
| chmod +x conf$$.sh | |||
| if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then | |||
| PATH_SEPARATOR=';' | |||
| else | |||
| PATH_SEPARATOR=: | |||
| fi | |||
| rm -f conf$$.sh | |||
| fi | |||
| ac_prog=ld | |||
| if test "$GCC" = yes; then | |||
| # Check if gcc -print-prog-name=ld gives a path. | |||
| AC_MSG_CHECKING([for ld used by GCC]) | |||
| case $host in | |||
| *-*-mingw*) | |||
| # gcc leaves a trailing carriage return which upsets mingw | |||
| ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; | |||
| *) | |||
| ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; | |||
| esac | |||
| case $ac_prog in | |||
| # Accept absolute paths. | |||
| [[\\/]* | [A-Za-z]:[\\/]*)] | |||
| [re_direlt='/[^/][^/]*/\.\./'] | |||
| # Canonicalize the path of ld | |||
| ac_prog=`echo $ac_prog| sed 's%\\\\%/%g'` | |||
| while echo $ac_prog | grep "$re_direlt" > /dev/null 2>&1; do | |||
| ac_prog=`echo $ac_prog| sed "s%$re_direlt%/%"` | |||
| done | |||
| test -z "$LD" && LD="$ac_prog" | |||
| ;; | |||
| "") | |||
| # If it fails, then pretend we aren't using GCC. | |||
| ac_prog=ld | |||
| ;; | |||
| *) | |||
| # If it is relative, then search for the first ld in PATH. | |||
| with_gnu_ld=unknown | |||
| ;; | |||
| esac | |||
| elif test "$with_gnu_ld" = yes; then | |||
| AC_MSG_CHECKING([for GNU ld]) | |||
| else | |||
| AC_MSG_CHECKING([for non-GNU ld]) | |||
| fi | |||
| AC_CACHE_VAL(acl_cv_path_LD, | |||
| [if test -z "$LD"; then | |||
| IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}${PATH_SEPARATOR-:}" | |||
| for ac_dir in $PATH; do | |||
| test -z "$ac_dir" && ac_dir=. | |||
| if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then | |||
| acl_cv_path_LD="$ac_dir/$ac_prog" | |||
| # Check to see if the program is GNU ld. I'd rather use --version, | |||
| # but apparently some GNU ld's only accept -v. | |||
| # Break only if it was the GNU/non-GNU ld that we prefer. | |||
| case `"$acl_cv_path_LD" -v 2>&1 < /dev/null` in | |||
| *GNU* | *'with BFD'*) | |||
| test "$with_gnu_ld" != no && break ;; | |||
| *) | |||
| test "$with_gnu_ld" != yes && break ;; | |||
| esac | |||
| fi | |||
| done | |||
| IFS="$ac_save_ifs" | |||
| else | |||
| acl_cv_path_LD="$LD" # Let the user override the test with a path. | |||
| fi]) | |||
| LD="$acl_cv_path_LD" | |||
| if test -n "$LD"; then | |||
| AC_MSG_RESULT($LD) | |||
| else | |||
| AC_MSG_RESULT(no) | |||
| fi | |||
| test -z "$LD" && AC_MSG_ERROR([no acceptable ld found in \$PATH]) | |||
| AC_LIB_PROG_LD_GNU | |||
| ]) | |||
| @@ -0,0 +1,709 @@ | |||
| # lib-link.m4 serial 13 (gettext-0.17) | |||
| dnl Copyright (C) 2001-2007 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl From Bruno Haible. | |||
| AC_PREREQ(2.54) | |||
| dnl AC_LIB_LINKFLAGS(name [, dependencies]) searches for libname and | |||
| dnl the libraries corresponding to explicit and implicit dependencies. | |||
| dnl Sets and AC_SUBSTs the LIB${NAME} and LTLIB${NAME} variables and | |||
| dnl augments the CPPFLAGS variable. | |||
| dnl Sets and AC_SUBSTs the LIB${NAME}_PREFIX variable to nonempty if libname | |||
| dnl was found in ${LIB${NAME}_PREFIX}/$acl_libdirstem. | |||
| AC_DEFUN([AC_LIB_LINKFLAGS], | |||
| [ | |||
| AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) | |||
| AC_REQUIRE([AC_LIB_RPATH]) | |||
| define([Name],[translit([$1],[./-], [___])]) | |||
| define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], | |||
| [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) | |||
| AC_CACHE_CHECK([how to link with lib[]$1], [ac_cv_lib[]Name[]_libs], [ | |||
| AC_LIB_LINKFLAGS_BODY([$1], [$2]) | |||
| ac_cv_lib[]Name[]_libs="$LIB[]NAME" | |||
| ac_cv_lib[]Name[]_ltlibs="$LTLIB[]NAME" | |||
| ac_cv_lib[]Name[]_cppflags="$INC[]NAME" | |||
| ac_cv_lib[]Name[]_prefix="$LIB[]NAME[]_PREFIX" | |||
| ]) | |||
| LIB[]NAME="$ac_cv_lib[]Name[]_libs" | |||
| LTLIB[]NAME="$ac_cv_lib[]Name[]_ltlibs" | |||
| INC[]NAME="$ac_cv_lib[]Name[]_cppflags" | |||
| LIB[]NAME[]_PREFIX="$ac_cv_lib[]Name[]_prefix" | |||
| AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME) | |||
| AC_SUBST([LIB]NAME) | |||
| AC_SUBST([LTLIB]NAME) | |||
| AC_SUBST([LIB]NAME[_PREFIX]) | |||
| dnl Also set HAVE_LIB[]NAME so that AC_LIB_HAVE_LINKFLAGS can reuse the | |||
| dnl results of this search when this library appears as a dependency. | |||
| HAVE_LIB[]NAME=yes | |||
| undefine([Name]) | |||
| undefine([NAME]) | |||
| ]) | |||
| dnl AC_LIB_HAVE_LINKFLAGS(name, dependencies, includes, testcode) | |||
| dnl searches for libname and the libraries corresponding to explicit and | |||
| dnl implicit dependencies, together with the specified include files and | |||
| dnl the ability to compile and link the specified testcode. If found, it | |||
| dnl sets and AC_SUBSTs HAVE_LIB${NAME}=yes and the LIB${NAME} and | |||
| dnl LTLIB${NAME} variables and augments the CPPFLAGS variable, and | |||
| dnl #defines HAVE_LIB${NAME} to 1. Otherwise, it sets and AC_SUBSTs | |||
| dnl HAVE_LIB${NAME}=no and LIB${NAME} and LTLIB${NAME} to empty. | |||
| dnl Sets and AC_SUBSTs the LIB${NAME}_PREFIX variable to nonempty if libname | |||
| dnl was found in ${LIB${NAME}_PREFIX}/$acl_libdirstem. | |||
| AC_DEFUN([AC_LIB_HAVE_LINKFLAGS], | |||
| [ | |||
| AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) | |||
| AC_REQUIRE([AC_LIB_RPATH]) | |||
| define([Name],[translit([$1],[./-], [___])]) | |||
| define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], | |||
| [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) | |||
| dnl Search for lib[]Name and define LIB[]NAME, LTLIB[]NAME and INC[]NAME | |||
| dnl accordingly. | |||
| AC_LIB_LINKFLAGS_BODY([$1], [$2]) | |||
| dnl Add $INC[]NAME to CPPFLAGS before performing the following checks, | |||
| dnl because if the user has installed lib[]Name and not disabled its use | |||
| dnl via --without-lib[]Name-prefix, he wants to use it. | |||
| ac_save_CPPFLAGS="$CPPFLAGS" | |||
| AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME) | |||
| AC_CACHE_CHECK([for lib[]$1], [ac_cv_lib[]Name], [ | |||
| ac_save_LIBS="$LIBS" | |||
| LIBS="$LIBS $LIB[]NAME" | |||
| AC_TRY_LINK([$3], [$4], [ac_cv_lib[]Name=yes], [ac_cv_lib[]Name=no]) | |||
| LIBS="$ac_save_LIBS" | |||
| ]) | |||
| if test "$ac_cv_lib[]Name" = yes; then | |||
| HAVE_LIB[]NAME=yes | |||
| AC_DEFINE([HAVE_LIB]NAME, 1, [Define if you have the $1 library.]) | |||
| AC_MSG_CHECKING([how to link with lib[]$1]) | |||
| AC_MSG_RESULT([$LIB[]NAME]) | |||
| else | |||
| HAVE_LIB[]NAME=no | |||
| dnl If $LIB[]NAME didn't lead to a usable library, we don't need | |||
| dnl $INC[]NAME either. | |||
| CPPFLAGS="$ac_save_CPPFLAGS" | |||
| LIB[]NAME= | |||
| LTLIB[]NAME= | |||
| LIB[]NAME[]_PREFIX= | |||
| fi | |||
| AC_SUBST([HAVE_LIB]NAME) | |||
| AC_SUBST([LIB]NAME) | |||
| AC_SUBST([LTLIB]NAME) | |||
| AC_SUBST([LIB]NAME[_PREFIX]) | |||
| undefine([Name]) | |||
| undefine([NAME]) | |||
| ]) | |||
| dnl Determine the platform dependent parameters needed to use rpath: | |||
| dnl acl_libext, | |||
| dnl acl_shlibext, | |||
| dnl acl_hardcode_libdir_flag_spec, | |||
| dnl acl_hardcode_libdir_separator, | |||
| dnl acl_hardcode_direct, | |||
| dnl acl_hardcode_minus_L. | |||
| AC_DEFUN([AC_LIB_RPATH], | |||
| [ | |||
| dnl Tell automake >= 1.10 to complain if config.rpath is missing. | |||
| m4_ifdef([AC_REQUIRE_AUX_FILE], [AC_REQUIRE_AUX_FILE([config.rpath])]) | |||
| AC_REQUIRE([AC_PROG_CC]) dnl we use $CC, $GCC, $LDFLAGS | |||
| AC_REQUIRE([AC_LIB_PROG_LD]) dnl we use $LD, $with_gnu_ld | |||
| AC_REQUIRE([AC_CANONICAL_HOST]) dnl we use $host | |||
| AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT]) dnl we use $ac_aux_dir | |||
| AC_CACHE_CHECK([for shared library run path origin], acl_cv_rpath, [ | |||
| CC="$CC" GCC="$GCC" LDFLAGS="$LDFLAGS" LD="$LD" with_gnu_ld="$with_gnu_ld" \ | |||
| ${CONFIG_SHELL-/bin/sh} "$ac_aux_dir/config.rpath" "$host" > conftest.sh | |||
| . ./conftest.sh | |||
| rm -f ./conftest.sh | |||
| acl_cv_rpath=done | |||
| ]) | |||
| wl="$acl_cv_wl" | |||
| acl_libext="$acl_cv_libext" | |||
| acl_shlibext="$acl_cv_shlibext" | |||
| acl_libname_spec="$acl_cv_libname_spec" | |||
| acl_library_names_spec="$acl_cv_library_names_spec" | |||
| acl_hardcode_libdir_flag_spec="$acl_cv_hardcode_libdir_flag_spec" | |||
| acl_hardcode_libdir_separator="$acl_cv_hardcode_libdir_separator" | |||
| acl_hardcode_direct="$acl_cv_hardcode_direct" | |||
| acl_hardcode_minus_L="$acl_cv_hardcode_minus_L" | |||
| dnl Determine whether the user wants rpath handling at all. | |||
| AC_ARG_ENABLE(rpath, | |||
| [ --disable-rpath do not hardcode runtime library paths], | |||
| :, enable_rpath=yes) | |||
| ]) | |||
| dnl AC_LIB_LINKFLAGS_BODY(name [, dependencies]) searches for libname and | |||
| dnl the libraries corresponding to explicit and implicit dependencies. | |||
| dnl Sets the LIB${NAME}, LTLIB${NAME} and INC${NAME} variables. | |||
| dnl Also, sets the LIB${NAME}_PREFIX variable to nonempty if libname was found | |||
| dnl in ${LIB${NAME}_PREFIX}/$acl_libdirstem. | |||
| AC_DEFUN([AC_LIB_LINKFLAGS_BODY], | |||
| [ | |||
| AC_REQUIRE([AC_LIB_PREPARE_MULTILIB]) | |||
| define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], | |||
| [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) | |||
| dnl Autoconf >= 2.61 supports dots in --with options. | |||
| define([N_A_M_E],[m4_if(m4_version_compare(m4_defn([m4_PACKAGE_VERSION]),[2.61]),[-1],[translit([$1],[.],[_])],[$1])]) | |||
| dnl By default, look in $includedir and $libdir. | |||
| use_additional=yes | |||
| AC_LIB_WITH_FINAL_PREFIX([ | |||
| eval additional_includedir=\"$includedir\" | |||
| eval additional_libdir=\"$libdir\" | |||
| ]) | |||
| AC_LIB_ARG_WITH([lib]N_A_M_E[-prefix], | |||
| [ --with-lib]N_A_M_E[-prefix[=DIR] search for lib$1 in DIR/include and DIR/lib | |||
| --without-lib]N_A_M_E[-prefix don't search for lib$1 in includedir and libdir], | |||
| [ | |||
| if test "X$withval" = "Xno"; then | |||
| use_additional=no | |||
| else | |||
| if test "X$withval" = "X"; then | |||
| AC_LIB_WITH_FINAL_PREFIX([ | |||
| eval additional_includedir=\"$includedir\" | |||
| eval additional_libdir=\"$libdir\" | |||
| ]) | |||
| else | |||
| additional_includedir="$withval/include" | |||
| additional_libdir="$withval/$acl_libdirstem" | |||
| fi | |||
| fi | |||
| ]) | |||
| dnl Search the library and its dependencies in $additional_libdir and | |||
| dnl $LDFLAGS. Using breadth-first-seach. | |||
| LIB[]NAME= | |||
| LTLIB[]NAME= | |||
| INC[]NAME= | |||
| LIB[]NAME[]_PREFIX= | |||
| rpathdirs= | |||
| ltrpathdirs= | |||
| names_already_handled= | |||
| names_next_round='$1 $2' | |||
| while test -n "$names_next_round"; do | |||
| names_this_round="$names_next_round" | |||
| names_next_round= | |||
| for name in $names_this_round; do | |||
| already_handled= | |||
| for n in $names_already_handled; do | |||
| if test "$n" = "$name"; then | |||
| already_handled=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$already_handled"; then | |||
| names_already_handled="$names_already_handled $name" | |||
| dnl See if it was already located by an earlier AC_LIB_LINKFLAGS | |||
| dnl or AC_LIB_HAVE_LINKFLAGS call. | |||
| uppername=`echo "$name" | sed -e 'y|abcdefghijklmnopqrstuvwxyz./-|ABCDEFGHIJKLMNOPQRSTUVWXYZ___|'` | |||
| eval value=\"\$HAVE_LIB$uppername\" | |||
| if test -n "$value"; then | |||
| if test "$value" = yes; then | |||
| eval value=\"\$LIB$uppername\" | |||
| test -z "$value" || LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$value" | |||
| eval value=\"\$LTLIB$uppername\" | |||
| test -z "$value" || LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$value" | |||
| else | |||
| dnl An earlier call to AC_LIB_HAVE_LINKFLAGS has determined | |||
| dnl that this library doesn't exist. So just drop it. | |||
| : | |||
| fi | |||
| else | |||
| dnl Search the library lib$name in $additional_libdir and $LDFLAGS | |||
| dnl and the already constructed $LIBNAME/$LTLIBNAME. | |||
| found_dir= | |||
| found_la= | |||
| found_so= | |||
| found_a= | |||
| eval libname=\"$acl_libname_spec\" # typically: libname=lib$name | |||
| if test -n "$acl_shlibext"; then | |||
| shrext=".$acl_shlibext" # typically: shrext=.so | |||
| else | |||
| shrext= | |||
| fi | |||
| if test $use_additional = yes; then | |||
| dir="$additional_libdir" | |||
| dnl The same code as in the loop below: | |||
| dnl First look for a shared library. | |||
| if test -n "$acl_shlibext"; then | |||
| if test -f "$dir/$libname$shrext"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$libname$shrext" | |||
| else | |||
| if test "$acl_library_names_spec" = '$libname$shrext$versuffix'; then | |||
| ver=`(cd "$dir" && \ | |||
| for f in "$libname$shrext".*; do echo "$f"; done \ | |||
| | sed -e "s,^$libname$shrext\\\\.,," \ | |||
| | sort -t '.' -n -r -k1,1 -k2,2 -k3,3 -k4,4 -k5,5 \ | |||
| | sed 1q ) 2>/dev/null` | |||
| if test -n "$ver" && test -f "$dir/$libname$shrext.$ver"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$libname$shrext.$ver" | |||
| fi | |||
| else | |||
| eval library_names=\"$acl_library_names_spec\" | |||
| for f in $library_names; do | |||
| if test -f "$dir/$f"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$f" | |||
| break | |||
| fi | |||
| done | |||
| fi | |||
| fi | |||
| fi | |||
| dnl Then look for a static library. | |||
| if test "X$found_dir" = "X"; then | |||
| if test -f "$dir/$libname.$acl_libext"; then | |||
| found_dir="$dir" | |||
| found_a="$dir/$libname.$acl_libext" | |||
| fi | |||
| fi | |||
| if test "X$found_dir" != "X"; then | |||
| if test -f "$dir/$libname.la"; then | |||
| found_la="$dir/$libname.la" | |||
| fi | |||
| fi | |||
| fi | |||
| if test "X$found_dir" = "X"; then | |||
| for x in $LDFLAGS $LTLIB[]NAME; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| case "$x" in | |||
| -L*) | |||
| dir=`echo "X$x" | sed -e 's/^X-L//'` | |||
| dnl First look for a shared library. | |||
| if test -n "$acl_shlibext"; then | |||
| if test -f "$dir/$libname$shrext"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$libname$shrext" | |||
| else | |||
| if test "$acl_library_names_spec" = '$libname$shrext$versuffix'; then | |||
| ver=`(cd "$dir" && \ | |||
| for f in "$libname$shrext".*; do echo "$f"; done \ | |||
| | sed -e "s,^$libname$shrext\\\\.,," \ | |||
| | sort -t '.' -n -r -k1,1 -k2,2 -k3,3 -k4,4 -k5,5 \ | |||
| | sed 1q ) 2>/dev/null` | |||
| if test -n "$ver" && test -f "$dir/$libname$shrext.$ver"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$libname$shrext.$ver" | |||
| fi | |||
| else | |||
| eval library_names=\"$acl_library_names_spec\" | |||
| for f in $library_names; do | |||
| if test -f "$dir/$f"; then | |||
| found_dir="$dir" | |||
| found_so="$dir/$f" | |||
| break | |||
| fi | |||
| done | |||
| fi | |||
| fi | |||
| fi | |||
| dnl Then look for a static library. | |||
| if test "X$found_dir" = "X"; then | |||
| if test -f "$dir/$libname.$acl_libext"; then | |||
| found_dir="$dir" | |||
| found_a="$dir/$libname.$acl_libext" | |||
| fi | |||
| fi | |||
| if test "X$found_dir" != "X"; then | |||
| if test -f "$dir/$libname.la"; then | |||
| found_la="$dir/$libname.la" | |||
| fi | |||
| fi | |||
| ;; | |||
| esac | |||
| if test "X$found_dir" != "X"; then | |||
| break | |||
| fi | |||
| done | |||
| fi | |||
| if test "X$found_dir" != "X"; then | |||
| dnl Found the library. | |||
| LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$found_dir -l$name" | |||
| if test "X$found_so" != "X"; then | |||
| dnl Linking with a shared library. We attempt to hardcode its | |||
| dnl directory into the executable's runpath, unless it's the | |||
| dnl standard /usr/lib. | |||
| if test "$enable_rpath" = no || test "X$found_dir" = "X/usr/$acl_libdirstem"; then | |||
| dnl No hardcoding is needed. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" | |||
| else | |||
| dnl Use an explicit option to hardcode DIR into the resulting | |||
| dnl binary. | |||
| dnl Potentially add DIR to ltrpathdirs. | |||
| dnl The ltrpathdirs will be appended to $LTLIBNAME at the end. | |||
| haveit= | |||
| for x in $ltrpathdirs; do | |||
| if test "X$x" = "X$found_dir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| ltrpathdirs="$ltrpathdirs $found_dir" | |||
| fi | |||
| dnl The hardcoding into $LIBNAME is system dependent. | |||
| if test "$acl_hardcode_direct" = yes; then | |||
| dnl Using DIR/libNAME.so during linking hardcodes DIR into the | |||
| dnl resulting binary. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" | |||
| else | |||
| if test -n "$acl_hardcode_libdir_flag_spec" && test "$acl_hardcode_minus_L" = no; then | |||
| dnl Use an explicit option to hardcode DIR into the resulting | |||
| dnl binary. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" | |||
| dnl Potentially add DIR to rpathdirs. | |||
| dnl The rpathdirs will be appended to $LIBNAME at the end. | |||
| haveit= | |||
| for x in $rpathdirs; do | |||
| if test "X$x" = "X$found_dir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| rpathdirs="$rpathdirs $found_dir" | |||
| fi | |||
| else | |||
| dnl Rely on "-L$found_dir". | |||
| dnl But don't add it if it's already contained in the LDFLAGS | |||
| dnl or the already constructed $LIBNAME | |||
| haveit= | |||
| for x in $LDFLAGS $LIB[]NAME; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-L$found_dir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir" | |||
| fi | |||
| if test "$acl_hardcode_minus_L" != no; then | |||
| dnl FIXME: Not sure whether we should use | |||
| dnl "-L$found_dir -l$name" or "-L$found_dir $found_so" | |||
| dnl here. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" | |||
| else | |||
| dnl We cannot use $acl_hardcode_runpath_var and LD_RUN_PATH | |||
| dnl here, because this doesn't fit in flags passed to the | |||
| dnl compiler. So give up. No hardcoding. This affects only | |||
| dnl very old systems. | |||
| dnl FIXME: Not sure whether we should use | |||
| dnl "-L$found_dir -l$name" or "-L$found_dir $found_so" | |||
| dnl here. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name" | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| else | |||
| if test "X$found_a" != "X"; then | |||
| dnl Linking with a static library. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_a" | |||
| else | |||
| dnl We shouldn't come here, but anyway it's good to have a | |||
| dnl fallback. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir -l$name" | |||
| fi | |||
| fi | |||
| dnl Assume the include files are nearby. | |||
| additional_includedir= | |||
| case "$found_dir" in | |||
| */$acl_libdirstem | */$acl_libdirstem/) | |||
| basedir=`echo "X$found_dir" | sed -e 's,^X,,' -e "s,/$acl_libdirstem/"'*$,,'` | |||
| LIB[]NAME[]_PREFIX="$basedir" | |||
| additional_includedir="$basedir/include" | |||
| ;; | |||
| esac | |||
| if test "X$additional_includedir" != "X"; then | |||
| dnl Potentially add $additional_includedir to $INCNAME. | |||
| dnl But don't add it | |||
| dnl 1. if it's the standard /usr/include, | |||
| dnl 2. if it's /usr/local/include and we are using GCC on Linux, | |||
| dnl 3. if it's already present in $CPPFLAGS or the already | |||
| dnl constructed $INCNAME, | |||
| dnl 4. if it doesn't exist as a directory. | |||
| if test "X$additional_includedir" != "X/usr/include"; then | |||
| haveit= | |||
| if test "X$additional_includedir" = "X/usr/local/include"; then | |||
| if test -n "$GCC"; then | |||
| case $host_os in | |||
| linux* | gnu* | k*bsd*-gnu) haveit=yes;; | |||
| esac | |||
| fi | |||
| fi | |||
| if test -z "$haveit"; then | |||
| for x in $CPPFLAGS $INC[]NAME; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-I$additional_includedir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| if test -d "$additional_includedir"; then | |||
| dnl Really add $additional_includedir to $INCNAME. | |||
| INC[]NAME="${INC[]NAME}${INC[]NAME:+ }-I$additional_includedir" | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| dnl Look for dependencies. | |||
| if test -n "$found_la"; then | |||
| dnl Read the .la file. It defines the variables | |||
| dnl dlname, library_names, old_library, dependency_libs, current, | |||
| dnl age, revision, installed, dlopen, dlpreopen, libdir. | |||
| save_libdir="$libdir" | |||
| case "$found_la" in | |||
| */* | *\\*) . "$found_la" ;; | |||
| *) . "./$found_la" ;; | |||
| esac | |||
| libdir="$save_libdir" | |||
| dnl We use only dependency_libs. | |||
| for dep in $dependency_libs; do | |||
| case "$dep" in | |||
| -L*) | |||
| additional_libdir=`echo "X$dep" | sed -e 's/^X-L//'` | |||
| dnl Potentially add $additional_libdir to $LIBNAME and $LTLIBNAME. | |||
| dnl But don't add it | |||
| dnl 1. if it's the standard /usr/lib, | |||
| dnl 2. if it's /usr/local/lib and we are using GCC on Linux, | |||
| dnl 3. if it's already present in $LDFLAGS or the already | |||
| dnl constructed $LIBNAME, | |||
| dnl 4. if it doesn't exist as a directory. | |||
| if test "X$additional_libdir" != "X/usr/$acl_libdirstem"; then | |||
| haveit= | |||
| if test "X$additional_libdir" = "X/usr/local/$acl_libdirstem"; then | |||
| if test -n "$GCC"; then | |||
| case $host_os in | |||
| linux* | gnu* | k*bsd*-gnu) haveit=yes;; | |||
| esac | |||
| fi | |||
| fi | |||
| if test -z "$haveit"; then | |||
| haveit= | |||
| for x in $LDFLAGS $LIB[]NAME; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-L$additional_libdir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| if test -d "$additional_libdir"; then | |||
| dnl Really add $additional_libdir to $LIBNAME. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$additional_libdir" | |||
| fi | |||
| fi | |||
| haveit= | |||
| for x in $LDFLAGS $LTLIB[]NAME; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-L$additional_libdir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| if test -d "$additional_libdir"; then | |||
| dnl Really add $additional_libdir to $LTLIBNAME. | |||
| LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$additional_libdir" | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| ;; | |||
| -R*) | |||
| dir=`echo "X$dep" | sed -e 's/^X-R//'` | |||
| if test "$enable_rpath" != no; then | |||
| dnl Potentially add DIR to rpathdirs. | |||
| dnl The rpathdirs will be appended to $LIBNAME at the end. | |||
| haveit= | |||
| for x in $rpathdirs; do | |||
| if test "X$x" = "X$dir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| rpathdirs="$rpathdirs $dir" | |||
| fi | |||
| dnl Potentially add DIR to ltrpathdirs. | |||
| dnl The ltrpathdirs will be appended to $LTLIBNAME at the end. | |||
| haveit= | |||
| for x in $ltrpathdirs; do | |||
| if test "X$x" = "X$dir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| ltrpathdirs="$ltrpathdirs $dir" | |||
| fi | |||
| fi | |||
| ;; | |||
| -l*) | |||
| dnl Handle this in the next round. | |||
| names_next_round="$names_next_round "`echo "X$dep" | sed -e 's/^X-l//'` | |||
| ;; | |||
| *.la) | |||
| dnl Handle this in the next round. Throw away the .la's | |||
| dnl directory; it is already contained in a preceding -L | |||
| dnl option. | |||
| names_next_round="$names_next_round "`echo "X$dep" | sed -e 's,^X.*/,,' -e 's,^lib,,' -e 's,\.la$,,'` | |||
| ;; | |||
| *) | |||
| dnl Most likely an immediate library name. | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$dep" | |||
| LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$dep" | |||
| ;; | |||
| esac | |||
| done | |||
| fi | |||
| else | |||
| dnl Didn't find the library; assume it is in the system directories | |||
| dnl known to the linker and runtime loader. (All the system | |||
| dnl directories known to the linker should also be known to the | |||
| dnl runtime loader, otherwise the system is severely misconfigured.) | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name" | |||
| LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-l$name" | |||
| fi | |||
| fi | |||
| fi | |||
| done | |||
| done | |||
| if test "X$rpathdirs" != "X"; then | |||
| if test -n "$acl_hardcode_libdir_separator"; then | |||
| dnl Weird platform: only the last -rpath option counts, the user must | |||
| dnl pass all path elements in one option. We can arrange that for a | |||
| dnl single library, but not when more than one $LIBNAMEs are used. | |||
| alldirs= | |||
| for found_dir in $rpathdirs; do | |||
| alldirs="${alldirs}${alldirs:+$acl_hardcode_libdir_separator}$found_dir" | |||
| done | |||
| dnl Note: acl_hardcode_libdir_flag_spec uses $libdir and $wl. | |||
| acl_save_libdir="$libdir" | |||
| libdir="$alldirs" | |||
| eval flag=\"$acl_hardcode_libdir_flag_spec\" | |||
| libdir="$acl_save_libdir" | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag" | |||
| else | |||
| dnl The -rpath options are cumulative. | |||
| for found_dir in $rpathdirs; do | |||
| acl_save_libdir="$libdir" | |||
| libdir="$found_dir" | |||
| eval flag=\"$acl_hardcode_libdir_flag_spec\" | |||
| libdir="$acl_save_libdir" | |||
| LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag" | |||
| done | |||
| fi | |||
| fi | |||
| if test "X$ltrpathdirs" != "X"; then | |||
| dnl When using libtool, the option that works for both libraries and | |||
| dnl executables is -R. The -R options are cumulative. | |||
| for found_dir in $ltrpathdirs; do | |||
| LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-R$found_dir" | |||
| done | |||
| fi | |||
| ]) | |||
| dnl AC_LIB_APPENDTOVAR(VAR, CONTENTS) appends the elements of CONTENTS to VAR, | |||
| dnl unless already present in VAR. | |||
| dnl Works only for CPPFLAGS, not for LIB* variables because that sometimes | |||
| dnl contains two or three consecutive elements that belong together. | |||
| AC_DEFUN([AC_LIB_APPENDTOVAR], | |||
| [ | |||
| for element in [$2]; do | |||
| haveit= | |||
| for x in $[$1]; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X$element"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| [$1]="${[$1]}${[$1]:+ }$element" | |||
| fi | |||
| done | |||
| ]) | |||
| dnl For those cases where a variable contains several -L and -l options | |||
| dnl referring to unknown libraries and directories, this macro determines the | |||
| dnl necessary additional linker options for the runtime path. | |||
| dnl AC_LIB_LINKFLAGS_FROM_LIBS([LDADDVAR], [LIBSVALUE], [USE-LIBTOOL]) | |||
| dnl sets LDADDVAR to linker options needed together with LIBSVALUE. | |||
| dnl If USE-LIBTOOL evaluates to non-empty, linking with libtool is assumed, | |||
| dnl otherwise linking without libtool is assumed. | |||
| AC_DEFUN([AC_LIB_LINKFLAGS_FROM_LIBS], | |||
| [ | |||
| AC_REQUIRE([AC_LIB_RPATH]) | |||
| AC_REQUIRE([AC_LIB_PREPARE_MULTILIB]) | |||
| $1= | |||
| if test "$enable_rpath" != no; then | |||
| if test -n "$acl_hardcode_libdir_flag_spec" && test "$acl_hardcode_minus_L" = no; then | |||
| dnl Use an explicit option to hardcode directories into the resulting | |||
| dnl binary. | |||
| rpathdirs= | |||
| next= | |||
| for opt in $2; do | |||
| if test -n "$next"; then | |||
| dir="$next" | |||
| dnl No need to hardcode the standard /usr/lib. | |||
| if test "X$dir" != "X/usr/$acl_libdirstem"; then | |||
| rpathdirs="$rpathdirs $dir" | |||
| fi | |||
| next= | |||
| else | |||
| case $opt in | |||
| -L) next=yes ;; | |||
| -L*) dir=`echo "X$opt" | sed -e 's,^X-L,,'` | |||
| dnl No need to hardcode the standard /usr/lib. | |||
| if test "X$dir" != "X/usr/$acl_libdirstem"; then | |||
| rpathdirs="$rpathdirs $dir" | |||
| fi | |||
| next= ;; | |||
| *) next= ;; | |||
| esac | |||
| fi | |||
| done | |||
| if test "X$rpathdirs" != "X"; then | |||
| if test -n ""$3""; then | |||
| dnl libtool is used for linking. Use -R options. | |||
| for dir in $rpathdirs; do | |||
| $1="${$1}${$1:+ }-R$dir" | |||
| done | |||
| else | |||
| dnl The linker is used for linking directly. | |||
| if test -n "$acl_hardcode_libdir_separator"; then | |||
| dnl Weird platform: only the last -rpath option counts, the user | |||
| dnl must pass all path elements in one option. | |||
| alldirs= | |||
| for dir in $rpathdirs; do | |||
| alldirs="${alldirs}${alldirs:+$acl_hardcode_libdir_separator}$dir" | |||
| done | |||
| acl_save_libdir="$libdir" | |||
| libdir="$alldirs" | |||
| eval flag=\"$acl_hardcode_libdir_flag_spec\" | |||
| libdir="$acl_save_libdir" | |||
| $1="$flag" | |||
| else | |||
| dnl The -rpath options are cumulative. | |||
| for dir in $rpathdirs; do | |||
| acl_save_libdir="$libdir" | |||
| libdir="$dir" | |||
| eval flag=\"$acl_hardcode_libdir_flag_spec\" | |||
| libdir="$acl_save_libdir" | |||
| $1="${$1}${$1:+ }$flag" | |||
| done | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| AC_SUBST([$1]) | |||
| ]) | |||
| @@ -0,0 +1,185 @@ | |||
| # lib-prefix.m4 serial 5 (gettext-0.15) | |||
| dnl Copyright (C) 2001-2005 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl From Bruno Haible. | |||
| dnl AC_LIB_ARG_WITH is synonymous to AC_ARG_WITH in autoconf-2.13, and | |||
| dnl similar to AC_ARG_WITH in autoconf 2.52...2.57 except that is doesn't | |||
| dnl require excessive bracketing. | |||
| ifdef([AC_HELP_STRING], | |||
| [AC_DEFUN([AC_LIB_ARG_WITH], [AC_ARG_WITH([$1],[[$2]],[$3],[$4])])], | |||
| [AC_DEFUN([AC_][LIB_ARG_WITH], [AC_ARG_WITH([$1],[$2],[$3],[$4])])]) | |||
| dnl AC_LIB_PREFIX adds to the CPPFLAGS and LDFLAGS the flags that are needed | |||
| dnl to access previously installed libraries. The basic assumption is that | |||
| dnl a user will want packages to use other packages he previously installed | |||
| dnl with the same --prefix option. | |||
| dnl This macro is not needed if only AC_LIB_LINKFLAGS is used to locate | |||
| dnl libraries, but is otherwise very convenient. | |||
| AC_DEFUN([AC_LIB_PREFIX], | |||
| [ | |||
| AC_BEFORE([$0], [AC_LIB_LINKFLAGS]) | |||
| AC_REQUIRE([AC_PROG_CC]) | |||
| AC_REQUIRE([AC_CANONICAL_HOST]) | |||
| AC_REQUIRE([AC_LIB_PREPARE_MULTILIB]) | |||
| AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) | |||
| dnl By default, look in $includedir and $libdir. | |||
| use_additional=yes | |||
| AC_LIB_WITH_FINAL_PREFIX([ | |||
| eval additional_includedir=\"$includedir\" | |||
| eval additional_libdir=\"$libdir\" | |||
| ]) | |||
| AC_LIB_ARG_WITH([lib-prefix], | |||
| [ --with-lib-prefix[=DIR] search for libraries in DIR/include and DIR/lib | |||
| --without-lib-prefix don't search for libraries in includedir and libdir], | |||
| [ | |||
| if test "X$withval" = "Xno"; then | |||
| use_additional=no | |||
| else | |||
| if test "X$withval" = "X"; then | |||
| AC_LIB_WITH_FINAL_PREFIX([ | |||
| eval additional_includedir=\"$includedir\" | |||
| eval additional_libdir=\"$libdir\" | |||
| ]) | |||
| else | |||
| additional_includedir="$withval/include" | |||
| additional_libdir="$withval/$acl_libdirstem" | |||
| fi | |||
| fi | |||
| ]) | |||
| if test $use_additional = yes; then | |||
| dnl Potentially add $additional_includedir to $CPPFLAGS. | |||
| dnl But don't add it | |||
| dnl 1. if it's the standard /usr/include, | |||
| dnl 2. if it's already present in $CPPFLAGS, | |||
| dnl 3. if it's /usr/local/include and we are using GCC on Linux, | |||
| dnl 4. if it doesn't exist as a directory. | |||
| if test "X$additional_includedir" != "X/usr/include"; then | |||
| haveit= | |||
| for x in $CPPFLAGS; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-I$additional_includedir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| if test "X$additional_includedir" = "X/usr/local/include"; then | |||
| if test -n "$GCC"; then | |||
| case $host_os in | |||
| linux* | gnu* | k*bsd*-gnu) haveit=yes;; | |||
| esac | |||
| fi | |||
| fi | |||
| if test -z "$haveit"; then | |||
| if test -d "$additional_includedir"; then | |||
| dnl Really add $additional_includedir to $CPPFLAGS. | |||
| CPPFLAGS="${CPPFLAGS}${CPPFLAGS:+ }-I$additional_includedir" | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| dnl Potentially add $additional_libdir to $LDFLAGS. | |||
| dnl But don't add it | |||
| dnl 1. if it's the standard /usr/lib, | |||
| dnl 2. if it's already present in $LDFLAGS, | |||
| dnl 3. if it's /usr/local/lib and we are using GCC on Linux, | |||
| dnl 4. if it doesn't exist as a directory. | |||
| if test "X$additional_libdir" != "X/usr/$acl_libdirstem"; then | |||
| haveit= | |||
| for x in $LDFLAGS; do | |||
| AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) | |||
| if test "X$x" = "X-L$additional_libdir"; then | |||
| haveit=yes | |||
| break | |||
| fi | |||
| done | |||
| if test -z "$haveit"; then | |||
| if test "X$additional_libdir" = "X/usr/local/$acl_libdirstem"; then | |||
| if test -n "$GCC"; then | |||
| case $host_os in | |||
| linux*) haveit=yes;; | |||
| esac | |||
| fi | |||
| fi | |||
| if test -z "$haveit"; then | |||
| if test -d "$additional_libdir"; then | |||
| dnl Really add $additional_libdir to $LDFLAGS. | |||
| LDFLAGS="${LDFLAGS}${LDFLAGS:+ }-L$additional_libdir" | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| fi | |||
| ]) | |||
| dnl AC_LIB_PREPARE_PREFIX creates variables acl_final_prefix, | |||
| dnl acl_final_exec_prefix, containing the values to which $prefix and | |||
| dnl $exec_prefix will expand at the end of the configure script. | |||
| AC_DEFUN([AC_LIB_PREPARE_PREFIX], | |||
| [ | |||
| dnl Unfortunately, prefix and exec_prefix get only finally determined | |||
| dnl at the end of configure. | |||
| if test "X$prefix" = "XNONE"; then | |||
| acl_final_prefix="$ac_default_prefix" | |||
| else | |||
| acl_final_prefix="$prefix" | |||
| fi | |||
| if test "X$exec_prefix" = "XNONE"; then | |||
| acl_final_exec_prefix='${prefix}' | |||
| else | |||
| acl_final_exec_prefix="$exec_prefix" | |||
| fi | |||
| acl_save_prefix="$prefix" | |||
| prefix="$acl_final_prefix" | |||
| eval acl_final_exec_prefix=\"$acl_final_exec_prefix\" | |||
| prefix="$acl_save_prefix" | |||
| ]) | |||
| dnl AC_LIB_WITH_FINAL_PREFIX([statement]) evaluates statement, with the | |||
| dnl variables prefix and exec_prefix bound to the values they will have | |||
| dnl at the end of the configure script. | |||
| AC_DEFUN([AC_LIB_WITH_FINAL_PREFIX], | |||
| [ | |||
| acl_save_prefix="$prefix" | |||
| prefix="$acl_final_prefix" | |||
| acl_save_exec_prefix="$exec_prefix" | |||
| exec_prefix="$acl_final_exec_prefix" | |||
| $1 | |||
| exec_prefix="$acl_save_exec_prefix" | |||
| prefix="$acl_save_prefix" | |||
| ]) | |||
| dnl AC_LIB_PREPARE_MULTILIB creates a variable acl_libdirstem, containing | |||
| dnl the basename of the libdir, either "lib" or "lib64". | |||
| AC_DEFUN([AC_LIB_PREPARE_MULTILIB], | |||
| [ | |||
| dnl There is no formal standard regarding lib and lib64. The current | |||
| dnl practice is that on a system supporting 32-bit and 64-bit instruction | |||
| dnl sets or ABIs, 64-bit libraries go under $prefix/lib64 and 32-bit | |||
| dnl libraries go under $prefix/lib. We determine the compiler's default | |||
| dnl mode by looking at the compiler's library search path. If at least | |||
| dnl of its elements ends in /lib64 or points to a directory whose absolute | |||
| dnl pathname ends in /lib64, we assume a 64-bit ABI. Otherwise we use the | |||
| dnl default, namely "lib". | |||
| acl_libdirstem=lib | |||
| searchpath=`(LC_ALL=C $CC -print-search-dirs) 2>/dev/null | sed -n -e 's,^libraries: ,,p' | sed -e 's,^=,,'` | |||
| if test -n "$searchpath"; then | |||
| acl_save_IFS="${IFS= }"; IFS=":" | |||
| for searchdir in $searchpath; do | |||
| if test -d "$searchdir"; then | |||
| case "$searchdir" in | |||
| */lib64/ | */lib64 ) acl_libdirstem=lib64 ;; | |||
| *) searchdir=`cd "$searchdir" && pwd` | |||
| case "$searchdir" in | |||
| */lib64 ) acl_libdirstem=lib64 ;; | |||
| esac ;; | |||
| esac | |||
| fi | |||
| done | |||
| IFS="$acl_save_IFS" | |||
| fi | |||
| ]) | |||
| @@ -0,0 +1,31 @@ | |||
| # nls.m4 serial 3 (gettext-0.15) | |||
| dnl Copyright (C) 1995-2003, 2005-2006 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl | |||
| dnl This file can can be used in projects which are not available under | |||
| dnl the GNU General Public License or the GNU Library General Public | |||
| dnl License but which still want to provide support for the GNU gettext | |||
| dnl functionality. | |||
| dnl Please note that the actual code of the GNU gettext library is covered | |||
| dnl by the GNU Library General Public License, and the rest of the GNU | |||
| dnl gettext package package is covered by the GNU General Public License. | |||
| dnl They are *not* in the public domain. | |||
| dnl Authors: | |||
| dnl Ulrich Drepper <drepper@cygnus.com>, 1995-2000. | |||
| dnl Bruno Haible <haible@clisp.cons.org>, 2000-2003. | |||
| AC_PREREQ(2.50) | |||
| AC_DEFUN([AM_NLS], | |||
| [ | |||
| AC_MSG_CHECKING([whether NLS is requested]) | |||
| dnl Default is enabled NLS | |||
| AC_ARG_ENABLE(nls, | |||
| [ --disable-nls do not use Native Language Support], | |||
| USE_NLS=$enableval, USE_NLS=yes) | |||
| AC_MSG_RESULT($USE_NLS) | |||
| AC_SUBST(USE_NLS) | |||
| ]) | |||
| @@ -0,0 +1,449 @@ | |||
| # po.m4 serial 15 (gettext-0.17) | |||
| dnl Copyright (C) 1995-2007 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl | |||
| dnl This file can can be used in projects which are not available under | |||
| dnl the GNU General Public License or the GNU Library General Public | |||
| dnl License but which still want to provide support for the GNU gettext | |||
| dnl functionality. | |||
| dnl Please note that the actual code of the GNU gettext library is covered | |||
| dnl by the GNU Library General Public License, and the rest of the GNU | |||
| dnl gettext package package is covered by the GNU General Public License. | |||
| dnl They are *not* in the public domain. | |||
| dnl Authors: | |||
| dnl Ulrich Drepper <drepper@cygnus.com>, 1995-2000. | |||
| dnl Bruno Haible <haible@clisp.cons.org>, 2000-2003. | |||
| AC_PREREQ(2.50) | |||
| dnl Checks for all prerequisites of the po subdirectory. | |||
| AC_DEFUN([AM_PO_SUBDIRS], | |||
| [ | |||
| AC_REQUIRE([AC_PROG_MAKE_SET])dnl | |||
| AC_REQUIRE([AC_PROG_INSTALL])dnl | |||
| AC_REQUIRE([AM_PROG_MKDIR_P])dnl defined by automake | |||
| AC_REQUIRE([AM_NLS])dnl | |||
| dnl Release version of the gettext macros. This is used to ensure that | |||
| dnl the gettext macros and po/Makefile.in.in are in sync. | |||
| AC_SUBST([GETTEXT_MACRO_VERSION], [0.17]) | |||
| dnl Perform the following tests also if --disable-nls has been given, | |||
| dnl because they are needed for "make dist" to work. | |||
| dnl Search for GNU msgfmt in the PATH. | |||
| dnl The first test excludes Solaris msgfmt and early GNU msgfmt versions. | |||
| dnl The second test excludes FreeBSD msgfmt. | |||
| AM_PATH_PROG_WITH_TEST(MSGFMT, msgfmt, | |||
| [$ac_dir/$ac_word --statistics /dev/null >&]AS_MESSAGE_LOG_FD[ 2>&1 && | |||
| (if $ac_dir/$ac_word --statistics /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)], | |||
| :) | |||
| AC_PATH_PROG(GMSGFMT, gmsgfmt, $MSGFMT) | |||
| dnl Test whether it is GNU msgfmt >= 0.15. | |||
| changequote(,)dnl | |||
| case `$MSGFMT --version | sed 1q | sed -e 's,^[^0-9]*,,'` in | |||
| '' | 0.[0-9] | 0.[0-9].* | 0.1[0-4] | 0.1[0-4].*) MSGFMT_015=: ;; | |||
| *) MSGFMT_015=$MSGFMT ;; | |||
| esac | |||
| changequote([,])dnl | |||
| AC_SUBST([MSGFMT_015]) | |||
| changequote(,)dnl | |||
| case `$GMSGFMT --version | sed 1q | sed -e 's,^[^0-9]*,,'` in | |||
| '' | 0.[0-9] | 0.[0-9].* | 0.1[0-4] | 0.1[0-4].*) GMSGFMT_015=: ;; | |||
| *) GMSGFMT_015=$GMSGFMT ;; | |||
| esac | |||
| changequote([,])dnl | |||
| AC_SUBST([GMSGFMT_015]) | |||
| dnl Search for GNU xgettext 0.12 or newer in the PATH. | |||
| dnl The first test excludes Solaris xgettext and early GNU xgettext versions. | |||
| dnl The second test excludes FreeBSD xgettext. | |||
| AM_PATH_PROG_WITH_TEST(XGETTEXT, xgettext, | |||
| [$ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null >&]AS_MESSAGE_LOG_FD[ 2>&1 && | |||
| (if $ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)], | |||
| :) | |||
| dnl Remove leftover from FreeBSD xgettext call. | |||
| rm -f messages.po | |||
| dnl Test whether it is GNU xgettext >= 0.15. | |||
| changequote(,)dnl | |||
| case `$XGETTEXT --version | sed 1q | sed -e 's,^[^0-9]*,,'` in | |||
| '' | 0.[0-9] | 0.[0-9].* | 0.1[0-4] | 0.1[0-4].*) XGETTEXT_015=: ;; | |||
| *) XGETTEXT_015=$XGETTEXT ;; | |||
| esac | |||
| changequote([,])dnl | |||
| AC_SUBST([XGETTEXT_015]) | |||
| dnl Search for GNU msgmerge 0.11 or newer in the PATH. | |||
| AM_PATH_PROG_WITH_TEST(MSGMERGE, msgmerge, | |||
| [$ac_dir/$ac_word --update -q /dev/null /dev/null >&]AS_MESSAGE_LOG_FD[ 2>&1], :) | |||
| dnl Installation directories. | |||
| dnl Autoconf >= 2.60 defines localedir. For older versions of autoconf, we | |||
| dnl have to define it here, so that it can be used in po/Makefile. | |||
| test -n "$localedir" || localedir='${datadir}/locale' | |||
| AC_SUBST([localedir]) | |||
| dnl Support for AM_XGETTEXT_OPTION. | |||
| test -n "${XGETTEXT_EXTRA_OPTIONS+set}" || XGETTEXT_EXTRA_OPTIONS= | |||
| AC_SUBST([XGETTEXT_EXTRA_OPTIONS]) | |||
| AC_CONFIG_COMMANDS([po-directories], [[ | |||
| for ac_file in $CONFIG_FILES; do | |||
| # Support "outfile[:infile[:infile...]]" | |||
| case "$ac_file" in | |||
| *:*) ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; | |||
| esac | |||
| # PO directories have a Makefile.in generated from Makefile.in.in. | |||
| case "$ac_file" in */Makefile.in) | |||
| # Adjust a relative srcdir. | |||
| ac_dir=`echo "$ac_file"|sed 's%/[^/][^/]*$%%'` | |||
| ac_dir_suffix="/`echo "$ac_dir"|sed 's%^\./%%'`" | |||
| ac_dots=`echo "$ac_dir_suffix"|sed 's%/[^/]*%../%g'` | |||
| # In autoconf-2.13 it is called $ac_given_srcdir. | |||
| # In autoconf-2.50 it is called $srcdir. | |||
| test -n "$ac_given_srcdir" || ac_given_srcdir="$srcdir" | |||
| case "$ac_given_srcdir" in | |||
| .) top_srcdir=`echo $ac_dots|sed 's%/$%%'` ;; | |||
| /*) top_srcdir="$ac_given_srcdir" ;; | |||
| *) top_srcdir="$ac_dots$ac_given_srcdir" ;; | |||
| esac | |||
| # Treat a directory as a PO directory if and only if it has a | |||
| # POTFILES.in file. This allows packages to have multiple PO | |||
| # directories under different names or in different locations. | |||
| if test -f "$ac_given_srcdir/$ac_dir/POTFILES.in"; then | |||
| rm -f "$ac_dir/POTFILES" | |||
| test -n "$as_me" && echo "$as_me: creating $ac_dir/POTFILES" || echo "creating $ac_dir/POTFILES" | |||
| cat "$ac_given_srcdir/$ac_dir/POTFILES.in" | sed -e "/^#/d" -e "/^[ ]*\$/d" -e "s,.*, $top_srcdir/& \\\\," | sed -e "\$s/\(.*\) \\\\/\1/" > "$ac_dir/POTFILES" | |||
| POMAKEFILEDEPS="POTFILES.in" | |||
| # ALL_LINGUAS, POFILES, UPDATEPOFILES, DUMMYPOFILES, GMOFILES depend | |||
| # on $ac_dir but don't depend on user-specified configuration | |||
| # parameters. | |||
| if test -f "$ac_given_srcdir/$ac_dir/LINGUAS"; then | |||
| # The LINGUAS file contains the set of available languages. | |||
| if test -n "$OBSOLETE_ALL_LINGUAS"; then | |||
| test -n "$as_me" && echo "$as_me: setting ALL_LINGUAS in configure.in is obsolete" || echo "setting ALL_LINGUAS in configure.in is obsolete" | |||
| fi | |||
| ALL_LINGUAS_=`sed -e "/^#/d" -e "s/#.*//" "$ac_given_srcdir/$ac_dir/LINGUAS"` | |||
| # Hide the ALL_LINGUAS assigment from automake < 1.5. | |||
| eval 'ALL_LINGUAS''=$ALL_LINGUAS_' | |||
| POMAKEFILEDEPS="$POMAKEFILEDEPS LINGUAS" | |||
| else | |||
| # The set of available languages was given in configure.in. | |||
| # Hide the ALL_LINGUAS assigment from automake < 1.5. | |||
| eval 'ALL_LINGUAS''=$OBSOLETE_ALL_LINGUAS' | |||
| fi | |||
| # Compute POFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(lang).po) | |||
| # Compute UPDATEPOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(lang).po-update) | |||
| # Compute DUMMYPOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(lang).nop) | |||
| # Compute GMOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(lang).gmo) | |||
| case "$ac_given_srcdir" in | |||
| .) srcdirpre= ;; | |||
| *) srcdirpre='$(srcdir)/' ;; | |||
| esac | |||
| POFILES= | |||
| UPDATEPOFILES= | |||
| DUMMYPOFILES= | |||
| GMOFILES= | |||
| for lang in $ALL_LINGUAS; do | |||
| POFILES="$POFILES $srcdirpre$lang.po" | |||
| UPDATEPOFILES="$UPDATEPOFILES $lang.po-update" | |||
| DUMMYPOFILES="$DUMMYPOFILES $lang.nop" | |||
| GMOFILES="$GMOFILES $srcdirpre$lang.gmo" | |||
| done | |||
| # CATALOGS depends on both $ac_dir and the user's LINGUAS | |||
| # environment variable. | |||
| INST_LINGUAS= | |||
| if test -n "$ALL_LINGUAS"; then | |||
| for presentlang in $ALL_LINGUAS; do | |||
| useit=no | |||
| if test "%UNSET%" != "$LINGUAS"; then | |||
| desiredlanguages="$LINGUAS" | |||
| else | |||
| desiredlanguages="$ALL_LINGUAS" | |||
| fi | |||
| for desiredlang in $desiredlanguages; do | |||
| # Use the presentlang catalog if desiredlang is | |||
| # a. equal to presentlang, or | |||
| # b. a variant of presentlang (because in this case, | |||
| # presentlang can be used as a fallback for messages | |||
| # which are not translated in the desiredlang catalog). | |||
| case "$desiredlang" in | |||
| "$presentlang"*) useit=yes;; | |||
| esac | |||
| done | |||
| if test $useit = yes; then | |||
| INST_LINGUAS="$INST_LINGUAS $presentlang" | |||
| fi | |||
| done | |||
| fi | |||
| CATALOGS= | |||
| if test -n "$INST_LINGUAS"; then | |||
| for lang in $INST_LINGUAS; do | |||
| CATALOGS="$CATALOGS $lang.gmo" | |||
| done | |||
| fi | |||
| test -n "$as_me" && echo "$as_me: creating $ac_dir/Makefile" || echo "creating $ac_dir/Makefile" | |||
| sed -e "/^POTFILES =/r $ac_dir/POTFILES" -e "/^# Makevars/r $ac_given_srcdir/$ac_dir/Makevars" -e "s|@POFILES@|$POFILES|g" -e "s|@UPDATEPOFILES@|$UPDATEPOFILES|g" -e "s|@DUMMYPOFILES@|$DUMMYPOFILES|g" -e "s|@GMOFILES@|$GMOFILES|g" -e "s|@CATALOGS@|$CATALOGS|g" -e "s|@POMAKEFILEDEPS@|$POMAKEFILEDEPS|g" "$ac_dir/Makefile.in" > "$ac_dir/Makefile" | |||
| for f in "$ac_given_srcdir/$ac_dir"/Rules-*; do | |||
| if test -f "$f"; then | |||
| case "$f" in | |||
| *.orig | *.bak | *~) ;; | |||
| *) cat "$f" >> "$ac_dir/Makefile" ;; | |||
| esac | |||
| fi | |||
| done | |||
| fi | |||
| ;; | |||
| esac | |||
| done]], | |||
| [# Capture the value of obsolete ALL_LINGUAS because we need it to compute | |||
| # POFILES, UPDATEPOFILES, DUMMYPOFILES, GMOFILES, CATALOGS. But hide it | |||
| # from automake < 1.5. | |||
| eval 'OBSOLETE_ALL_LINGUAS''="$ALL_LINGUAS"' | |||
| # Capture the value of LINGUAS because we need it to compute CATALOGS. | |||
| LINGUAS="${LINGUAS-%UNSET%}" | |||
| ]) | |||
| ]) | |||
| dnl Postprocesses a Makefile in a directory containing PO files. | |||
| AC_DEFUN([AM_POSTPROCESS_PO_MAKEFILE], | |||
| [ | |||
| # When this code is run, in config.status, two variables have already been | |||
| # set: | |||
| # - OBSOLETE_ALL_LINGUAS is the value of LINGUAS set in configure.in, | |||
| # - LINGUAS is the value of the environment variable LINGUAS at configure | |||
| # time. | |||
| changequote(,)dnl | |||
| # Adjust a relative srcdir. | |||
| ac_dir=`echo "$ac_file"|sed 's%/[^/][^/]*$%%'` | |||
| ac_dir_suffix="/`echo "$ac_dir"|sed 's%^\./%%'`" | |||
| ac_dots=`echo "$ac_dir_suffix"|sed 's%/[^/]*%../%g'` | |||
| # In autoconf-2.13 it is called $ac_given_srcdir. | |||
| # In autoconf-2.50 it is called $srcdir. | |||
| test -n "$ac_given_srcdir" || ac_given_srcdir="$srcdir" | |||
| case "$ac_given_srcdir" in | |||
| .) top_srcdir=`echo $ac_dots|sed 's%/$%%'` ;; | |||
| /*) top_srcdir="$ac_given_srcdir" ;; | |||
| *) top_srcdir="$ac_dots$ac_given_srcdir" ;; | |||
| esac | |||
| # Find a way to echo strings without interpreting backslash. | |||
| if test "X`(echo '\t') 2>/dev/null`" = 'X\t'; then | |||
| gt_echo='echo' | |||
| else | |||
| if test "X`(printf '%s\n' '\t') 2>/dev/null`" = 'X\t'; then | |||
| gt_echo='printf %s\n' | |||
| else | |||
| echo_func () { | |||
| cat <<EOT | |||
| $* | |||
| EOT | |||
| } | |||
| gt_echo='echo_func' | |||
| fi | |||
| fi | |||
| # A sed script that extracts the value of VARIABLE from a Makefile. | |||
| sed_x_variable=' | |||
| # Test if the hold space is empty. | |||
| x | |||
| s/P/P/ | |||
| x | |||
| ta | |||
| # Yes it was empty. Look if we have the expected variable definition. | |||
| /^[ ]*VARIABLE[ ]*=/{ | |||
| # Seen the first line of the variable definition. | |||
| s/^[ ]*VARIABLE[ ]*=// | |||
| ba | |||
| } | |||
| bd | |||
| :a | |||
| # Here we are processing a line from the variable definition. | |||
| # Remove comment, more precisely replace it with a space. | |||
| s/#.*$/ / | |||
| # See if the line ends in a backslash. | |||
| tb | |||
| :b | |||
| s/\\$// | |||
| # Print the line, without the trailing backslash. | |||
| p | |||
| tc | |||
| # There was no trailing backslash. The end of the variable definition is | |||
| # reached. Clear the hold space. | |||
| s/^.*$// | |||
| x | |||
| bd | |||
| :c | |||
| # A trailing backslash means that the variable definition continues in the | |||
| # next line. Put a nonempty string into the hold space to indicate this. | |||
| s/^.*$/P/ | |||
| x | |||
| :d | |||
| ' | |||
| changequote([,])dnl | |||
| # Set POTFILES to the value of the Makefile variable POTFILES. | |||
| sed_x_POTFILES=`$gt_echo "$sed_x_variable" | sed -e '/^ *#/d' -e 's/VARIABLE/POTFILES/g'` | |||
| POTFILES=`sed -n -e "$sed_x_POTFILES" < "$ac_file"` | |||
| # Compute POTFILES_DEPS as | |||
| # $(foreach file, $(POTFILES), $(top_srcdir)/$(file)) | |||
| POTFILES_DEPS= | |||
| for file in $POTFILES; do | |||
| POTFILES_DEPS="$POTFILES_DEPS "'$(top_srcdir)/'"$file" | |||
| done | |||
| POMAKEFILEDEPS="" | |||
| if test -n "$OBSOLETE_ALL_LINGUAS"; then | |||
| test -n "$as_me" && echo "$as_me: setting ALL_LINGUAS in configure.in is obsolete" || echo "setting ALL_LINGUAS in configure.in is obsolete" | |||
| fi | |||
| if test -f "$ac_given_srcdir/$ac_dir/LINGUAS"; then | |||
| # The LINGUAS file contains the set of available languages. | |||
| ALL_LINGUAS_=`sed -e "/^#/d" -e "s/#.*//" "$ac_given_srcdir/$ac_dir/LINGUAS"` | |||
| POMAKEFILEDEPS="$POMAKEFILEDEPS LINGUAS" | |||
| else | |||
| # Set ALL_LINGUAS to the value of the Makefile variable LINGUAS. | |||
| sed_x_LINGUAS=`$gt_echo "$sed_x_variable" | sed -e '/^ *#/d' -e 's/VARIABLE/LINGUAS/g'` | |||
| ALL_LINGUAS_=`sed -n -e "$sed_x_LINGUAS" < "$ac_file"` | |||
| fi | |||
| # Hide the ALL_LINGUAS assigment from automake < 1.5. | |||
| eval 'ALL_LINGUAS''=$ALL_LINGUAS_' | |||
| # Compute POFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(lang).po) | |||
| # Compute UPDATEPOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(lang).po-update) | |||
| # Compute DUMMYPOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(lang).nop) | |||
| # Compute GMOFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(lang).gmo) | |||
| # Compute PROPERTIESFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(top_srcdir)/$(DOMAIN)_$(lang).properties) | |||
| # Compute CLASSFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(top_srcdir)/$(DOMAIN)_$(lang).class) | |||
| # Compute QMFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(lang).qm) | |||
| # Compute MSGFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(frob $(lang)).msg) | |||
| # Compute RESOURCESDLLFILES | |||
| # as $(foreach lang, $(ALL_LINGUAS), $(srcdir)/$(frob $(lang))/$(DOMAIN).resources.dll) | |||
| case "$ac_given_srcdir" in | |||
| .) srcdirpre= ;; | |||
| *) srcdirpre='$(srcdir)/' ;; | |||
| esac | |||
| POFILES= | |||
| UPDATEPOFILES= | |||
| DUMMYPOFILES= | |||
| GMOFILES= | |||
| PROPERTIESFILES= | |||
| CLASSFILES= | |||
| QMFILES= | |||
| MSGFILES= | |||
| RESOURCESDLLFILES= | |||
| for lang in $ALL_LINGUAS; do | |||
| POFILES="$POFILES $srcdirpre$lang.po" | |||
| UPDATEPOFILES="$UPDATEPOFILES $lang.po-update" | |||
| DUMMYPOFILES="$DUMMYPOFILES $lang.nop" | |||
| GMOFILES="$GMOFILES $srcdirpre$lang.gmo" | |||
| PROPERTIESFILES="$PROPERTIESFILES \$(top_srcdir)/\$(DOMAIN)_$lang.properties" | |||
| CLASSFILES="$CLASSFILES \$(top_srcdir)/\$(DOMAIN)_$lang.class" | |||
| QMFILES="$QMFILES $srcdirpre$lang.qm" | |||
| frobbedlang=`echo $lang | sed -e 's/\..*$//' -e 'y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/'` | |||
| MSGFILES="$MSGFILES $srcdirpre$frobbedlang.msg" | |||
| frobbedlang=`echo $lang | sed -e 's/_/-/g' -e 's/^sr-CS/sr-SP/' -e 's/@latin$/-Latn/' -e 's/@cyrillic$/-Cyrl/' -e 's/^sr-SP$/sr-SP-Latn/' -e 's/^uz-UZ$/uz-UZ-Latn/'` | |||
| RESOURCESDLLFILES="$RESOURCESDLLFILES $srcdirpre$frobbedlang/\$(DOMAIN).resources.dll" | |||
| done | |||
| # CATALOGS depends on both $ac_dir and the user's LINGUAS | |||
| # environment variable. | |||
| INST_LINGUAS= | |||
| if test -n "$ALL_LINGUAS"; then | |||
| for presentlang in $ALL_LINGUAS; do | |||
| useit=no | |||
| if test "%UNSET%" != "$LINGUAS"; then | |||
| desiredlanguages="$LINGUAS" | |||
| else | |||
| desiredlanguages="$ALL_LINGUAS" | |||
| fi | |||
| for desiredlang in $desiredlanguages; do | |||
| # Use the presentlang catalog if desiredlang is | |||
| # a. equal to presentlang, or | |||
| # b. a variant of presentlang (because in this case, | |||
| # presentlang can be used as a fallback for messages | |||
| # which are not translated in the desiredlang catalog). | |||
| case "$desiredlang" in | |||
| "$presentlang"*) useit=yes;; | |||
| esac | |||
| done | |||
| if test $useit = yes; then | |||
| INST_LINGUAS="$INST_LINGUAS $presentlang" | |||
| fi | |||
| done | |||
| fi | |||
| CATALOGS= | |||
| JAVACATALOGS= | |||
| QTCATALOGS= | |||
| TCLCATALOGS= | |||
| CSHARPCATALOGS= | |||
| if test -n "$INST_LINGUAS"; then | |||
| for lang in $INST_LINGUAS; do | |||
| CATALOGS="$CATALOGS $lang.gmo" | |||
| JAVACATALOGS="$JAVACATALOGS \$(DOMAIN)_$lang.properties" | |||
| QTCATALOGS="$QTCATALOGS $lang.qm" | |||
| frobbedlang=`echo $lang | sed -e 's/\..*$//' -e 'y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/'` | |||
| TCLCATALOGS="$TCLCATALOGS $frobbedlang.msg" | |||
| frobbedlang=`echo $lang | sed -e 's/_/-/g' -e 's/^sr-CS/sr-SP/' -e 's/@latin$/-Latn/' -e 's/@cyrillic$/-Cyrl/' -e 's/^sr-SP$/sr-SP-Latn/' -e 's/^uz-UZ$/uz-UZ-Latn/'` | |||
| CSHARPCATALOGS="$CSHARPCATALOGS $frobbedlang/\$(DOMAIN).resources.dll" | |||
| done | |||
| fi | |||
| sed -e "s|@POTFILES_DEPS@|$POTFILES_DEPS|g" -e "s|@POFILES@|$POFILES|g" -e "s|@UPDATEPOFILES@|$UPDATEPOFILES|g" -e "s|@DUMMYPOFILES@|$DUMMYPOFILES|g" -e "s|@GMOFILES@|$GMOFILES|g" -e "s|@PROPERTIESFILES@|$PROPERTIESFILES|g" -e "s|@CLASSFILES@|$CLASSFILES|g" -e "s|@QMFILES@|$QMFILES|g" -e "s|@MSGFILES@|$MSGFILES|g" -e "s|@RESOURCESDLLFILES@|$RESOURCESDLLFILES|g" -e "s|@CATALOGS@|$CATALOGS|g" -e "s|@JAVACATALOGS@|$JAVACATALOGS|g" -e "s|@QTCATALOGS@|$QTCATALOGS|g" -e "s|@TCLCATALOGS@|$TCLCATALOGS|g" -e "s|@CSHARPCATALOGS@|$CSHARPCATALOGS|g" -e 's,^#distdir:,distdir:,' < "$ac_file" > "$ac_file.tmp" | |||
| if grep -l '@TCLCATALOGS@' "$ac_file" > /dev/null; then | |||
| # Add dependencies that cannot be formulated as a simple suffix rule. | |||
| for lang in $ALL_LINGUAS; do | |||
| frobbedlang=`echo $lang | sed -e 's/\..*$//' -e 'y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/'` | |||
| cat >> "$ac_file.tmp" <<EOF | |||
| $frobbedlang.msg: $lang.po | |||
| @echo "\$(MSGFMT) -c --tcl -d \$(srcdir) -l $lang $srcdirpre$lang.po"; \ | |||
| \$(MSGFMT) -c --tcl -d "\$(srcdir)" -l $lang $srcdirpre$lang.po || { rm -f "\$(srcdir)/$frobbedlang.msg"; exit 1; } | |||
| EOF | |||
| done | |||
| fi | |||
| if grep -l '@CSHARPCATALOGS@' "$ac_file" > /dev/null; then | |||
| # Add dependencies that cannot be formulated as a simple suffix rule. | |||
| for lang in $ALL_LINGUAS; do | |||
| frobbedlang=`echo $lang | sed -e 's/_/-/g' -e 's/^sr-CS/sr-SP/' -e 's/@latin$/-Latn/' -e 's/@cyrillic$/-Cyrl/' -e 's/^sr-SP$/sr-SP-Latn/' -e 's/^uz-UZ$/uz-UZ-Latn/'` | |||
| cat >> "$ac_file.tmp" <<EOF | |||
| $frobbedlang/\$(DOMAIN).resources.dll: $lang.po | |||
| @echo "\$(MSGFMT) -c --csharp -d \$(srcdir) -l $lang $srcdirpre$lang.po -r \$(DOMAIN)"; \ | |||
| \$(MSGFMT) -c --csharp -d "\$(srcdir)" -l $lang $srcdirpre$lang.po -r "\$(DOMAIN)" || { rm -f "\$(srcdir)/$frobbedlang.msg"; exit 1; } | |||
| EOF | |||
| done | |||
| fi | |||
| if test -n "$POMAKEFILEDEPS"; then | |||
| cat >> "$ac_file.tmp" <<EOF | |||
| Makefile: $POMAKEFILEDEPS | |||
| EOF | |||
| fi | |||
| mv "$ac_file.tmp" "$ac_file" | |||
| ]) | |||
| dnl Initializes the accumulator used by AM_XGETTEXT_OPTION. | |||
| AC_DEFUN([AM_XGETTEXT_OPTION_INIT], | |||
| [ | |||
| XGETTEXT_EXTRA_OPTIONS= | |||
| ]) | |||
| dnl Registers an option to be passed to xgettext in the po subdirectory. | |||
| AC_DEFUN([AM_XGETTEXT_OPTION], | |||
| [ | |||
| AC_REQUIRE([AM_XGETTEXT_OPTION_INIT]) | |||
| XGETTEXT_EXTRA_OPTIONS="$XGETTEXT_EXTRA_OPTIONS $1" | |||
| ]) | |||
| @@ -0,0 +1,92 @@ | |||
| # progtest.m4 serial 4 (gettext-0.14.2) | |||
| dnl Copyright (C) 1996-2003, 2005 Free Software Foundation, Inc. | |||
| dnl This file is free software; the Free Software Foundation | |||
| dnl gives unlimited permission to copy and/or distribute it, | |||
| dnl with or without modifications, as long as this notice is preserved. | |||
| dnl | |||
| dnl This file can can be used in projects which are not available under | |||
| dnl the GNU General Public License or the GNU Library General Public | |||
| dnl License but which still want to provide support for the GNU gettext | |||
| dnl functionality. | |||
| dnl Please note that the actual code of the GNU gettext library is covered | |||
| dnl by the GNU Library General Public License, and the rest of the GNU | |||
| dnl gettext package package is covered by the GNU General Public License. | |||
| dnl They are *not* in the public domain. | |||
| dnl Authors: | |||
| dnl Ulrich Drepper <drepper@cygnus.com>, 1996. | |||
| AC_PREREQ(2.50) | |||
| # Search path for a program which passes the given test. | |||
| dnl AM_PATH_PROG_WITH_TEST(VARIABLE, PROG-TO-CHECK-FOR, | |||
| dnl TEST-PERFORMED-ON-FOUND_PROGRAM [, VALUE-IF-NOT-FOUND [, PATH]]) | |||
| AC_DEFUN([AM_PATH_PROG_WITH_TEST], | |||
| [ | |||
| # Prepare PATH_SEPARATOR. | |||
| # The user is always right. | |||
| if test "${PATH_SEPARATOR+set}" != set; then | |||
| echo "#! /bin/sh" >conf$$.sh | |||
| echo "exit 0" >>conf$$.sh | |||
| chmod +x conf$$.sh | |||
| if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then | |||
| PATH_SEPARATOR=';' | |||
| else | |||
| PATH_SEPARATOR=: | |||
| fi | |||
| rm -f conf$$.sh | |||
| fi | |||
| # Find out how to test for executable files. Don't use a zero-byte file, | |||
| # as systems may use methods other than mode bits to determine executability. | |||
| cat >conf$$.file <<_ASEOF | |||
| #! /bin/sh | |||
| exit 0 | |||
| _ASEOF | |||
| chmod +x conf$$.file | |||
| if test -x conf$$.file >/dev/null 2>&1; then | |||
| ac_executable_p="test -x" | |||
| else | |||
| ac_executable_p="test -f" | |||
| fi | |||
| rm -f conf$$.file | |||
| # Extract the first word of "$2", so it can be a program name with args. | |||
| set dummy $2; ac_word=[$]2 | |||
| AC_MSG_CHECKING([for $ac_word]) | |||
| AC_CACHE_VAL(ac_cv_path_$1, | |||
| [case "[$]$1" in | |||
| [[\\/]]* | ?:[[\\/]]*) | |||
| ac_cv_path_$1="[$]$1" # Let the user override the test with a path. | |||
| ;; | |||
| *) | |||
| ac_save_IFS="$IFS"; IFS=$PATH_SEPARATOR | |||
| for ac_dir in ifelse([$5], , $PATH, [$5]); do | |||
| IFS="$ac_save_IFS" | |||
| test -z "$ac_dir" && ac_dir=. | |||
| for ac_exec_ext in '' $ac_executable_extensions; do | |||
| if $ac_executable_p "$ac_dir/$ac_word$ac_exec_ext"; then | |||
| echo "$as_me: trying $ac_dir/$ac_word..." >&AS_MESSAGE_LOG_FD | |||
| if [$3]; then | |||
| ac_cv_path_$1="$ac_dir/$ac_word$ac_exec_ext" | |||
| break 2 | |||
| fi | |||
| fi | |||
| done | |||
| done | |||
| IFS="$ac_save_IFS" | |||
| dnl If no 4th arg is given, leave the cache variable unset, | |||
| dnl so AC_PATH_PROGS will keep looking. | |||
| ifelse([$4], , , [ test -z "[$]ac_cv_path_$1" && ac_cv_path_$1="$4" | |||
| ])dnl | |||
| ;; | |||
| esac])dnl | |||
| $1="$ac_cv_path_$1" | |||
| if test ifelse([$4], , [-n "[$]$1"], ["[$]$1" != "$4"]); then | |||
| AC_MSG_RESULT([$]$1) | |||
| else | |||
| AC_MSG_RESULT(no) | |||
| fi | |||
| AC_SUBST($1)dnl | |||
| ]) | |||
| @@ -0,0 +1,128 @@ | |||
| dnl @synopsis VL_PROG_CC_WARNINGS([ANSI]) | |||
| dnl | |||
| dnl Enables a high level of warnings for the C compiler. Optionally, | |||
| dnl if the first argument is nonempty, turns on flags which enforce and/or | |||
| dnl enable proper ANSI C if such are known with the compiler used. | |||
| dnl | |||
| dnl Currently this macro knows about GCC, Solaris C compiler, | |||
| dnl Digital Unix C compiler, C for AIX Compiler, HP-UX C compiler, | |||
| dnl IRIX C compiler, NEC SX-5 (Super-UX 10) C compiler, and Cray J90 | |||
| dnl (Unicos 10.0.0.8) C compiler. | |||
| dnl | |||
| dnl @version 1.2 | |||
| dnl @author Ville Laurikari <vl@iki.fi> | |||
| dnl | |||
| AC_DEFUN([VL_PROG_CC_WARNINGS], [ | |||
| # Don't override if CFLAGS was already set. | |||
| if test -z "$ac_env_CFLAGS_set"; then | |||
| ansi=$1 | |||
| if test -z "$ansi"; then | |||
| msg="for C compiler warning flags" | |||
| else | |||
| msg="for C compiler warning and ANSI conformance flags" | |||
| fi | |||
| AC_CACHE_CHECK($msg, vl_cv_prog_cc_warnings, [ | |||
| if test -n "$CC"; then | |||
| cat > conftest.c <<EOF | |||
| int main(int argc, char **argv) { return 0; } | |||
| EOF | |||
| dnl GCC | |||
| if test "$GCC" = "yes"; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-Wall" | |||
| else | |||
| vl_cv_prog_cc_warnings="-Wall -ansi -pedantic" | |||
| fi | |||
| dnl Most compilers print some kind of a version string with some command | |||
| dnl line options (often "-V"). The version string should be checked | |||
| dnl before doing a test compilation run with compiler-specific flags. | |||
| dnl This is because some compilers (like the Cray compiler) only | |||
| dnl produce a warning message for unknown flags instead of returning | |||
| dnl an error, resulting in a false positive. Also, compilers may do | |||
| dnl erratic things when invoked with flags meant for a different | |||
| dnl compiler. | |||
| dnl Solaris C compiler | |||
| elif $CC -V 2>&1 | grep -i "WorkShop" > /dev/null 2>&1 && | |||
| $CC -c -v -Xc conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-v" | |||
| else | |||
| vl_cv_prog_cc_warnings="-v -Xc" | |||
| fi | |||
| dnl Compaq (formerly Digital Unix) C compiler | |||
| elif ($CC -V 2>&1 | grep -i "Digital UNIX Compiler" > /dev/null 2>&1 || | |||
| $CC -V 2>&1 | grep -i "Compaq C" > /dev/null 2>&1) && | |||
| $CC -c -verbose -w0 -warnprotos -std1 conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-verbose -w0 -warnprotos" | |||
| else | |||
| vl_cv_prog_cc_warnings="-verbose -w0 -warnprotos -std1" | |||
| fi | |||
| dnl C for AIX Compiler | |||
| elif $CC 2>&1 | grep -i "C for AIX Compiler" > /dev/null 2>&1 && | |||
| $CC -c -qlanglvl=ansi -qinfo=all conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-qsrcmsg -qinfo=all:noppt:noppc:noobs:nocnd:nouni:nocnv" | |||
| else | |||
| vl_cv_prog_cc_warnings="-qsrcmsg -qinfo=all:noppt:noppc:noobs:nocnd:nouni:nocnv -qlanglvl=ansi" | |||
| fi | |||
| dnl IRIX C compiler | |||
| elif $CC -version 2>&1 | grep -i "MIPSpro Compilers" > /dev/null 2>&1 && | |||
| $CC -c -fullwarn -ansi -ansiE conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-fullwarn" | |||
| else | |||
| vl_cv_prog_cc_warnings="-fullwarn -ansi -ansiE" | |||
| fi | |||
| dnl HP-UX C compiler | |||
| elif what $CC 2>&1 | grep -i "HP C Compiler" > /dev/null 2>&1 && | |||
| $CC -c -Aa +w1 conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="+w1" | |||
| else | |||
| vl_cv_prog_cc_warnings="+w1 -Aa" | |||
| fi | |||
| dnl The NEC SX-5 (Super-UX 10) C compiler | |||
| elif $CC -V 2>&1 | grep "/SX" > /dev/null 2>&1 && | |||
| $CC -c -pvctl[,]fullmsg -Xc conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-pvctl[,]fullmsg" | |||
| else | |||
| vl_cv_prog_cc_warnings="-pvctl[,]fullmsg -Xc" | |||
| fi | |||
| dnl The Cray C compiler (Unicos) | |||
| elif $CC -V 2>&1 | grep -i "Cray" > /dev/null 2>&1 && | |||
| $CC -c -h msglevel 2 conftest.c > /dev/null 2>&1 && | |||
| test -f conftest.o; then | |||
| if test -z "$ansi"; then | |||
| vl_cv_prog_cc_warnings="-h msglevel 2" | |||
| else | |||
| vl_cv_prog_cc_warnings="-h msglevel 2 -h conform" | |||
| fi | |||
| fi | |||
| rm -f conftest.* | |||
| fi | |||
| if test -n "$vl_cv_prog_cc_warnings"; then | |||
| CFLAGS="$CFLAGS $vl_cv_prog_cc_warnings" | |||
| else | |||
| vl_cv_prog_cc_warnings="unknown" | |||
| fi | |||
| ]) | |||
| fi | |||
| ])dnl | |||
| @@ -0,0 +1,3 @@ | |||
| # Set of available languages. | |||
| fi | |||
| sv | |||
| @@ -0,0 +1,429 @@ | |||
| # Makefile for PO directory in any package using GNU gettext. | |||
| # Copyright (C) 1995-1997, 2000-2007 by Ulrich Drepper <drepper@gnu.ai.mit.edu> | |||
| # | |||
| # This file can be copied and used freely without restrictions. It can | |||
| # be used in projects which are not available under the GNU General Public | |||
| # License but which still want to provide support for the GNU gettext | |||
| # functionality. | |||
| # Please note that the actual code of GNU gettext is covered by the GNU | |||
| # General Public License and is *not* in the public domain. | |||
| # | |||
| # Origin: gettext-0.17 | |||
| GETTEXT_MACRO_VERSION = 0.17 | |||
| PACKAGE = @PACKAGE@ | |||
| VERSION = @VERSION@ | |||
| PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ | |||
| SHELL = /bin/sh | |||
| @SET_MAKE@ | |||
| srcdir = @srcdir@ | |||
| top_srcdir = @top_srcdir@ | |||
| VPATH = @srcdir@ | |||
| prefix = @prefix@ | |||
| exec_prefix = @exec_prefix@ | |||
| datarootdir = @datarootdir@ | |||
| datadir = @datadir@ | |||
| localedir = @localedir@ | |||
| gettextsrcdir = $(datadir)/gettext/po | |||
| INSTALL = @INSTALL@ | |||
| INSTALL_DATA = @INSTALL_DATA@ | |||
| # We use $(mkdir_p). | |||
| # In automake <= 1.9.x, $(mkdir_p) is defined either as "mkdir -p --" or as | |||
| # "$(mkinstalldirs)" or as "$(install_sh) -d". For these automake versions, | |||
| # @install_sh@ does not start with $(SHELL), so we add it. | |||
| # In automake >= 1.10, @mkdir_p@ is derived from ${MKDIR_P}, which is defined | |||
| # either as "/path/to/mkdir -p" or ".../install-sh -c -d". For these automake | |||
| # versions, $(mkinstalldirs) and $(install_sh) are unused. | |||
| mkinstalldirs = $(SHELL) @install_sh@ -d | |||
| install_sh = $(SHELL) @install_sh@ | |||
| MKDIR_P = @MKDIR_P@ | |||
| mkdir_p = @mkdir_p@ | |||
| GMSGFMT_ = @GMSGFMT@ | |||
| GMSGFMT_no = @GMSGFMT@ | |||
| GMSGFMT_yes = @GMSGFMT_015@ | |||
| GMSGFMT = $(GMSGFMT_$(USE_MSGCTXT)) | |||
| MSGFMT_ = @MSGFMT@ | |||
| MSGFMT_no = @MSGFMT@ | |||
| MSGFMT_yes = @MSGFMT_015@ | |||
| MSGFMT = $(MSGFMT_$(USE_MSGCTXT)) | |||
| XGETTEXT_ = @XGETTEXT@ | |||
| XGETTEXT_no = @XGETTEXT@ | |||
| XGETTEXT_yes = @XGETTEXT_015@ | |||
| XGETTEXT = $(XGETTEXT_$(USE_MSGCTXT)) | |||
| MSGMERGE = msgmerge | |||
| MSGMERGE_UPDATE = @MSGMERGE@ --update | |||
| MSGINIT = msginit | |||
| MSGCONV = msgconv | |||
| MSGFILTER = msgfilter | |||
| POFILES = @POFILES@ | |||
| GMOFILES = @GMOFILES@ | |||
| UPDATEPOFILES = @UPDATEPOFILES@ | |||
| DUMMYPOFILES = @DUMMYPOFILES@ | |||
| DISTFILES.common = Makefile.in.in remove-potcdate.sin \ | |||
| $(DISTFILES.common.extra1) $(DISTFILES.common.extra2) $(DISTFILES.common.extra3) | |||
| DISTFILES = $(DISTFILES.common) Makevars POTFILES.in \ | |||
| $(POFILES) $(GMOFILES) \ | |||
| $(DISTFILES.extra1) $(DISTFILES.extra2) $(DISTFILES.extra3) | |||
| POTFILES = \ | |||
| CATALOGS = @CATALOGS@ | |||
| # Makevars gets inserted here. (Don't remove this line!) | |||
| .SUFFIXES: | |||
| .SUFFIXES: .po .gmo .mo .sed .sin .nop .po-create .po-update | |||
| .po.mo: | |||
| @echo "$(MSGFMT) -c -o $@ $<"; \ | |||
| $(MSGFMT) -c -o t-$@ $< && mv t-$@ $@ | |||
| .po.gmo: | |||
| @lang=`echo $* | sed -e 's,.*/,,'`; \ | |||
| test "$(srcdir)" = . && cdcmd="" || cdcmd="cd $(srcdir) && "; \ | |||
| echo "$${cdcmd}rm -f $${lang}.gmo && $(GMSGFMT) -c --statistics -o $${lang}.gmo $${lang}.po"; \ | |||
| cd $(srcdir) && rm -f $${lang}.gmo && $(GMSGFMT) -c --statistics -o t-$${lang}.gmo $${lang}.po && mv t-$${lang}.gmo $${lang}.gmo | |||
| .sin.sed: | |||
| sed -e '/^#/d' $< > t-$@ | |||
| mv t-$@ $@ | |||
| all: check-macro-version all-@USE_NLS@ | |||
| all-yes: stamp-po | |||
| all-no: | |||
| # Ensure that the gettext macros and this Makefile.in.in are in sync. | |||
| check-macro-version: | |||
| @test "$(GETTEXT_MACRO_VERSION)" = "@GETTEXT_MACRO_VERSION@" \ | |||
| || { echo "*** error: gettext infrastructure mismatch: using a Makefile.in.in from gettext version $(GETTEXT_MACRO_VERSION) but the autoconf macros are from gettext version @GETTEXT_MACRO_VERSION@" 1>&2; \ | |||
| exit 1; \ | |||
| } | |||
| # $(srcdir)/$(DOMAIN).pot is only created when needed. When xgettext finds no | |||
| # internationalized messages, no $(srcdir)/$(DOMAIN).pot is created (because | |||
| # we don't want to bother translators with empty POT files). We assume that | |||
| # LINGUAS is empty in this case, i.e. $(POFILES) and $(GMOFILES) are empty. | |||
| # In this case, stamp-po is a nop (i.e. a phony target). | |||
| # stamp-po is a timestamp denoting the last time at which the CATALOGS have | |||
| # been loosely updated. Its purpose is that when a developer or translator | |||
| # checks out the package via CVS, and the $(DOMAIN).pot file is not in CVS, | |||
| # "make" will update the $(DOMAIN).pot and the $(CATALOGS), but subsequent | |||
| # invocations of "make" will do nothing. This timestamp would not be necessary | |||
| # if updating the $(CATALOGS) would always touch them; however, the rule for | |||
| # $(POFILES) has been designed to not touch files that don't need to be | |||
| # changed. | |||
| stamp-po: $(srcdir)/$(DOMAIN).pot | |||
| test ! -f $(srcdir)/$(DOMAIN).pot || \ | |||
| test -z "$(GMOFILES)" || $(MAKE) $(GMOFILES) | |||
| @test ! -f $(srcdir)/$(DOMAIN).pot || { \ | |||
| echo "touch stamp-po" && \ | |||
| echo timestamp > stamp-poT && \ | |||
| mv stamp-poT stamp-po; \ | |||
| } | |||
| # Note: Target 'all' must not depend on target '$(DOMAIN).pot-update', | |||
| # otherwise packages like GCC can not be built if only parts of the source | |||
| # have been downloaded. | |||
| # This target rebuilds $(DOMAIN).pot; it is an expensive operation. | |||
| # Note that $(DOMAIN).pot is not touched if it doesn't need to be changed. | |||
| $(DOMAIN).pot-update: $(POTFILES) $(srcdir)/POTFILES.in remove-potcdate.sed | |||
| if LC_ALL=C grep 'GNU @PACKAGE@' $(top_srcdir)/* 2>/dev/null | grep -v 'libtool:' >/dev/null; then \ | |||
| package_gnu='GNU '; \ | |||
| else \ | |||
| package_gnu=''; \ | |||
| fi; \ | |||
| if test -n '$(MSGID_BUGS_ADDRESS)' || test '$(PACKAGE_BUGREPORT)' = '@'PACKAGE_BUGREPORT'@'; then \ | |||
| msgid_bugs_address='$(MSGID_BUGS_ADDRESS)'; \ | |||
| else \ | |||
| msgid_bugs_address='$(PACKAGE_BUGREPORT)'; \ | |||
| fi; \ | |||
| case `$(XGETTEXT) --version | sed 1q | sed -e 's,^[^0-9]*,,'` in \ | |||
| '' | 0.[0-9] | 0.[0-9].* | 0.1[0-5] | 0.1[0-5].* | 0.16 | 0.16.[0-1]*) \ | |||
| $(XGETTEXT) --default-domain=$(DOMAIN) --directory=$(top_srcdir) \ | |||
| --add-comments=TRANSLATORS: $(XGETTEXT_OPTIONS) @XGETTEXT_EXTRA_OPTIONS@ \ | |||
| --files-from=$(srcdir)/POTFILES.in \ | |||
| --copyright-holder='$(COPYRIGHT_HOLDER)' \ | |||
| --msgid-bugs-address="$$msgid_bugs_address" \ | |||
| ;; \ | |||
| *) \ | |||
| $(XGETTEXT) --default-domain=$(DOMAIN) --directory=$(top_srcdir) \ | |||
| --add-comments=TRANSLATORS: $(XGETTEXT_OPTIONS) @XGETTEXT_EXTRA_OPTIONS@ \ | |||
| --files-from=$(srcdir)/POTFILES.in \ | |||
| --copyright-holder='$(COPYRIGHT_HOLDER)' \ | |||
| --package-name="$${package_gnu}@PACKAGE@" \ | |||
| --package-version='@VERSION@' \ | |||
| --msgid-bugs-address="$$msgid_bugs_address" \ | |||
| ;; \ | |||
| esac | |||
| test ! -f $(DOMAIN).po || { \ | |||
| if test -f $(srcdir)/$(DOMAIN).pot; then \ | |||
| sed -f remove-potcdate.sed < $(srcdir)/$(DOMAIN).pot > $(DOMAIN).1po && \ | |||
| sed -f remove-potcdate.sed < $(DOMAIN).po > $(DOMAIN).2po && \ | |||
| if cmp $(DOMAIN).1po $(DOMAIN).2po >/dev/null 2>&1; then \ | |||
| rm -f $(DOMAIN).1po $(DOMAIN).2po $(DOMAIN).po; \ | |||
| else \ | |||
| rm -f $(DOMAIN).1po $(DOMAIN).2po $(srcdir)/$(DOMAIN).pot && \ | |||
| mv $(DOMAIN).po $(srcdir)/$(DOMAIN).pot; \ | |||
| fi; \ | |||
| else \ | |||
| mv $(DOMAIN).po $(srcdir)/$(DOMAIN).pot; \ | |||
| fi; \ | |||
| } | |||
| # This rule has no dependencies: we don't need to update $(DOMAIN).pot at | |||
| # every "make" invocation, only create it when it is missing. | |||
| # Only "make $(DOMAIN).pot-update" or "make dist" will force an update. | |||
| $(srcdir)/$(DOMAIN).pot: | |||
| $(MAKE) $(DOMAIN).pot-update | |||
| # This target rebuilds a PO file if $(DOMAIN).pot has changed. | |||
| # Note that a PO file is not touched if it doesn't need to be changed. | |||
| $(POFILES): $(srcdir)/$(DOMAIN).pot | |||
| @lang=`echo $@ | sed -e 's,.*/,,' -e 's/\.po$$//'`; \ | |||
| if test -f "$(srcdir)/$${lang}.po"; then \ | |||
| test "$(srcdir)" = . && cdcmd="" || cdcmd="cd $(srcdir) && "; \ | |||
| echo "$${cdcmd}$(MSGMERGE_UPDATE) $${lang}.po $(DOMAIN).pot"; \ | |||
| cd $(srcdir) && $(MSGMERGE_UPDATE) $${lang}.po $(DOMAIN).pot; \ | |||
| else \ | |||
| $(MAKE) $${lang}.po-create; \ | |||
| fi | |||
| install: install-exec install-data | |||
| install-exec: | |||
| install-data: install-data-@USE_NLS@ | |||
| if test "$(PACKAGE)" = "gettext-tools"; then \ | |||
| $(mkdir_p) $(DESTDIR)$(gettextsrcdir); \ | |||
| for file in $(DISTFILES.common) Makevars.template; do \ | |||
| $(INSTALL_DATA) $(srcdir)/$$file \ | |||
| $(DESTDIR)$(gettextsrcdir)/$$file; \ | |||
| done; \ | |||
| for file in Makevars; do \ | |||
| rm -f $(DESTDIR)$(gettextsrcdir)/$$file; \ | |||
| done; \ | |||
| else \ | |||
| : ; \ | |||
| fi | |||
| install-data-no: all | |||
| install-data-yes: all | |||
| $(mkdir_p) $(DESTDIR)$(datadir) | |||
| @catalogs='$(CATALOGS)'; \ | |||
| for cat in $$catalogs; do \ | |||
| cat=`basename $$cat`; \ | |||
| lang=`echo $$cat | sed -e 's/\.gmo$$//'`; \ | |||
| dir=$(localedir)/$$lang/LC_MESSAGES; \ | |||
| $(mkdir_p) $(DESTDIR)$$dir; \ | |||
| if test -r $$cat; then realcat=$$cat; else realcat=$(srcdir)/$$cat; fi; \ | |||
| $(INSTALL_DATA) $$realcat $(DESTDIR)$$dir/$(DOMAIN).mo; \ | |||
| echo "installing $$realcat as $(DESTDIR)$$dir/$(DOMAIN).mo"; \ | |||
| for lc in '' $(EXTRA_LOCALE_CATEGORIES); do \ | |||
| if test -n "$$lc"; then \ | |||
| if (cd $(DESTDIR)$(localedir)/$$lang && LC_ALL=C ls -l -d $$lc 2>/dev/null) | grep ' -> ' >/dev/null; then \ | |||
| link=`cd $(DESTDIR)$(localedir)/$$lang && LC_ALL=C ls -l -d $$lc | sed -e 's/^.* -> //'`; \ | |||
| mv $(DESTDIR)$(localedir)/$$lang/$$lc $(DESTDIR)$(localedir)/$$lang/$$lc.old; \ | |||
| mkdir $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| (cd $(DESTDIR)$(localedir)/$$lang/$$lc.old && \ | |||
| for file in *; do \ | |||
| if test -f $$file; then \ | |||
| ln -s ../$$link/$$file $(DESTDIR)$(localedir)/$$lang/$$lc/$$file; \ | |||
| fi; \ | |||
| done); \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc.old; \ | |||
| else \ | |||
| if test -d $(DESTDIR)$(localedir)/$$lang/$$lc; then \ | |||
| :; \ | |||
| else \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| mkdir $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| fi; \ | |||
| fi; \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo; \ | |||
| ln -s ../LC_MESSAGES/$(DOMAIN).mo $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo 2>/dev/null || \ | |||
| ln $(DESTDIR)$(localedir)/$$lang/LC_MESSAGES/$(DOMAIN).mo $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo 2>/dev/null || \ | |||
| cp -p $(DESTDIR)$(localedir)/$$lang/LC_MESSAGES/$(DOMAIN).mo $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo; \ | |||
| echo "installing $$realcat link as $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo"; \ | |||
| fi; \ | |||
| done; \ | |||
| done | |||
| install-strip: install | |||
| installdirs: installdirs-exec installdirs-data | |||
| installdirs-exec: | |||
| installdirs-data: installdirs-data-@USE_NLS@ | |||
| if test "$(PACKAGE)" = "gettext-tools"; then \ | |||
| $(mkdir_p) $(DESTDIR)$(gettextsrcdir); \ | |||
| else \ | |||
| : ; \ | |||
| fi | |||
| installdirs-data-no: | |||
| installdirs-data-yes: | |||
| $(mkdir_p) $(DESTDIR)$(datadir) | |||
| @catalogs='$(CATALOGS)'; \ | |||
| for cat in $$catalogs; do \ | |||
| cat=`basename $$cat`; \ | |||
| lang=`echo $$cat | sed -e 's/\.gmo$$//'`; \ | |||
| dir=$(localedir)/$$lang/LC_MESSAGES; \ | |||
| $(mkdir_p) $(DESTDIR)$$dir; \ | |||
| for lc in '' $(EXTRA_LOCALE_CATEGORIES); do \ | |||
| if test -n "$$lc"; then \ | |||
| if (cd $(DESTDIR)$(localedir)/$$lang && LC_ALL=C ls -l -d $$lc 2>/dev/null) | grep ' -> ' >/dev/null; then \ | |||
| link=`cd $(DESTDIR)$(localedir)/$$lang && LC_ALL=C ls -l -d $$lc | sed -e 's/^.* -> //'`; \ | |||
| mv $(DESTDIR)$(localedir)/$$lang/$$lc $(DESTDIR)$(localedir)/$$lang/$$lc.old; \ | |||
| mkdir $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| (cd $(DESTDIR)$(localedir)/$$lang/$$lc.old && \ | |||
| for file in *; do \ | |||
| if test -f $$file; then \ | |||
| ln -s ../$$link/$$file $(DESTDIR)$(localedir)/$$lang/$$lc/$$file; \ | |||
| fi; \ | |||
| done); \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc.old; \ | |||
| else \ | |||
| if test -d $(DESTDIR)$(localedir)/$$lang/$$lc; then \ | |||
| :; \ | |||
| else \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| mkdir $(DESTDIR)$(localedir)/$$lang/$$lc; \ | |||
| fi; \ | |||
| fi; \ | |||
| fi; \ | |||
| done; \ | |||
| done | |||
| # Define this as empty until I found a useful application. | |||
| installcheck: | |||
| uninstall: uninstall-exec uninstall-data | |||
| uninstall-exec: | |||
| uninstall-data: uninstall-data-@USE_NLS@ | |||
| if test "$(PACKAGE)" = "gettext-tools"; then \ | |||
| for file in $(DISTFILES.common) Makevars.template; do \ | |||
| rm -f $(DESTDIR)$(gettextsrcdir)/$$file; \ | |||
| done; \ | |||
| else \ | |||
| : ; \ | |||
| fi | |||
| uninstall-data-no: | |||
| uninstall-data-yes: | |||
| catalogs='$(CATALOGS)'; \ | |||
| for cat in $$catalogs; do \ | |||
| cat=`basename $$cat`; \ | |||
| lang=`echo $$cat | sed -e 's/\.gmo$$//'`; \ | |||
| for lc in LC_MESSAGES $(EXTRA_LOCALE_CATEGORIES); do \ | |||
| rm -f $(DESTDIR)$(localedir)/$$lang/$$lc/$(DOMAIN).mo; \ | |||
| done; \ | |||
| done | |||
| check: all | |||
| info dvi ps pdf html tags TAGS ctags CTAGS ID: | |||
| mostlyclean: | |||
| rm -f remove-potcdate.sed | |||
| rm -f stamp-poT | |||
| rm -f core core.* $(DOMAIN).po $(DOMAIN).1po $(DOMAIN).2po *.new.po | |||
| rm -fr *.o | |||
| clean: mostlyclean | |||
| distclean: clean | |||
| rm -f Makefile Makefile.in POTFILES *.mo | |||
| maintainer-clean: distclean | |||
| @echo "This command is intended for maintainers to use;" | |||
| @echo "it deletes files that may require special tools to rebuild." | |||
| rm -f stamp-po $(GMOFILES) | |||
| distdir = $(top_builddir)/$(PACKAGE)-$(VERSION)/$(subdir) | |||
| dist distdir: | |||
| $(MAKE) update-po | |||
| @$(MAKE) dist2 | |||
| # This is a separate target because 'update-po' must be executed before. | |||
| dist2: stamp-po $(DISTFILES) | |||
| dists="$(DISTFILES)"; \ | |||
| if test "$(PACKAGE)" = "gettext-tools"; then \ | |||
| dists="$$dists Makevars.template"; \ | |||
| fi; \ | |||
| if test -f $(srcdir)/$(DOMAIN).pot; then \ | |||
| dists="$$dists $(DOMAIN).pot stamp-po"; \ | |||
| fi; \ | |||
| if test -f $(srcdir)/ChangeLog; then \ | |||
| dists="$$dists ChangeLog"; \ | |||
| fi; \ | |||
| for i in 0 1 2 3 4 5 6 7 8 9; do \ | |||
| if test -f $(srcdir)/ChangeLog.$$i; then \ | |||
| dists="$$dists ChangeLog.$$i"; \ | |||
| fi; \ | |||
| done; \ | |||
| if test -f $(srcdir)/LINGUAS; then dists="$$dists LINGUAS"; fi; \ | |||
| for file in $$dists; do \ | |||
| if test -f $$file; then \ | |||
| cp -p $$file $(distdir) || exit 1; \ | |||
| else \ | |||
| cp -p $(srcdir)/$$file $(distdir) || exit 1; \ | |||
| fi; \ | |||
| done | |||
| update-po: Makefile | |||
| $(MAKE) $(DOMAIN).pot-update | |||
| test -z "$(UPDATEPOFILES)" || $(MAKE) $(UPDATEPOFILES) | |||
| $(MAKE) update-gmo | |||
| # General rule for creating PO files. | |||
| .nop.po-create: | |||
| @lang=`echo $@ | sed -e 's/\.po-create$$//'`; \ | |||
| echo "File $$lang.po does not exist. If you are a translator, you can create it through 'msginit'." 1>&2; \ | |||
| exit 1 | |||
| # General rule for updating PO files. | |||
| .nop.po-update: | |||
| @lang=`echo $@ | sed -e 's/\.po-update$$//'`; \ | |||
| if test "$(PACKAGE)" = "gettext-tools"; then PATH=`pwd`/../src:$$PATH; fi; \ | |||
| tmpdir=`pwd`; \ | |||
| echo "$$lang:"; \ | |||
| test "$(srcdir)" = . && cdcmd="" || cdcmd="cd $(srcdir) && "; \ | |||
| echo "$${cdcmd}$(MSGMERGE) $$lang.po $(DOMAIN).pot -o $$lang.new.po"; \ | |||
| cd $(srcdir); \ | |||
| if $(MSGMERGE) $$lang.po $(DOMAIN).pot -o $$tmpdir/$$lang.new.po; then \ | |||
| if cmp $$lang.po $$tmpdir/$$lang.new.po >/dev/null 2>&1; then \ | |||
| rm -f $$tmpdir/$$lang.new.po; \ | |||
| else \ | |||
| if mv -f $$tmpdir/$$lang.new.po $$lang.po; then \ | |||
| :; \ | |||
| else \ | |||
| echo "msgmerge for $$lang.po failed: cannot move $$tmpdir/$$lang.new.po to $$lang.po" 1>&2; \ | |||
| exit 1; \ | |||
| fi; \ | |||
| fi; \ | |||
| else \ | |||
| echo "msgmerge for $$lang.po failed!" 1>&2; \ | |||
| rm -f $$tmpdir/$$lang.new.po; \ | |||
| fi | |||
| $(DUMMYPOFILES): | |||
| update-gmo: Makefile $(GMOFILES) | |||
| @: | |||
| Makefile: Makefile.in.in Makevars $(top_builddir)/config.status @POMAKEFILEDEPS@ | |||
| cd $(top_builddir) \ | |||
| && $(SHELL) ./config.status $(subdir)/$@.in po-directories | |||
| force: | |||
| # Tell versions [3.59,3.63) of GNU make not to export all variables. | |||
| # Otherwise a system limit (for SysV at least) may be exceeded. | |||
| .NOEXPORT: | |||
| @@ -0,0 +1,41 @@ | |||
| # Makefile variables for PO directory in any package using GNU gettext. | |||
| # Usually the message domain is the same as the package name. | |||
| DOMAIN = $(PACKAGE) | |||
| # These two variables depend on the location of this directory. | |||
| subdir = po | |||
| top_builddir = .. | |||
| # These options get passed to xgettext. | |||
| XGETTEXT_OPTIONS = --keyword=_ --keyword=N_ | |||
| # This is the copyright holder that gets inserted into the header of the | |||
| # $(DOMAIN).pot file. Set this to the copyright holder of the surrounding | |||
| # package. (Note that the msgstr strings, extracted from the package's | |||
| # sources, belong to the copyright holder of the package.) Translators are | |||
| # expected to transfer the copyright for their translations to this person | |||
| # or entity, or to disclaim their copyright. The empty string stands for | |||
| # the public domain; in this case the translators are expected to disclaim | |||
| # their copyright. | |||
| COPYRIGHT_HOLDER = Ville Laurikari | |||
| # This is the email address or URL to which the translators shall report | |||
| # bugs in the untranslated strings: | |||
| # - Strings which are not entire sentences, see the maintainer guidelines | |||
| # in the GNU gettext documentation, section 'Preparing Strings'. | |||
| # - Strings which use unclear terms or require additional context to be | |||
| # understood. | |||
| # - Strings which make invalid assumptions about notation of date, time or | |||
| # money. | |||
| # - Pluralisation problems. | |||
| # - Incorrect English spelling. | |||
| # - Incorrect formatting. | |||
| # It can be your email address, or a mailing list address where translators | |||
| # can write to without being subscribed, or the URL of a web page through | |||
| # which the translators can contact you. | |||
| MSGID_BUGS_ADDRESS = tre-general@lists.laurikari.net | |||
| # This is the list of locale categories, beyond LC_MESSAGES, for which the | |||
| # message catalogs shall be used. It is usually empty. | |||
| EXTRA_LOCALE_CATEGORIES = | |||
| @@ -0,0 +1,7 @@ | |||
| # List of source files containing translatable strings. | |||
| # Library files | |||
| lib/regerror.c | |||
| # agrep files | |||
| src/agrep.c | |||
| @@ -0,0 +1,47 @@ | |||
| # Special Makefile rules for English message catalogs with quotation marks. | |||
| DISTFILES.common.extra1 = quot.sed boldquot.sed en@quot.header en@boldquot.header insert-header.sin Rules-quot | |||
| .SUFFIXES: .insert-header .po-update-en | |||
| en@quot.po-create: | |||
| $(MAKE) en@quot.po-update | |||
| en@boldquot.po-create: | |||
| $(MAKE) en@boldquot.po-update | |||
| en@quot.po-update: en@quot.po-update-en | |||
| en@boldquot.po-update: en@boldquot.po-update-en | |||
| .insert-header.po-update-en: | |||
| @lang=`echo $@ | sed -e 's/\.po-update-en$$//'`; \ | |||
| if test "$(PACKAGE)" = "gettext"; then PATH=`pwd`/../src:$$PATH; GETTEXTLIBDIR=`cd $(top_srcdir)/src && pwd`; export GETTEXTLIBDIR; fi; \ | |||
| tmpdir=`pwd`; \ | |||
| echo "$$lang:"; \ | |||
| ll=`echo $$lang | sed -e 's/@.*//'`; \ | |||
| LC_ALL=C; export LC_ALL; \ | |||
| cd $(srcdir); \ | |||
| if $(MSGINIT) -i $(DOMAIN).pot --no-translator -l $$ll -o - 2>/dev/null | sed -f $$tmpdir/$$lang.insert-header | $(MSGCONV) -t UTF-8 | $(MSGFILTER) sed -f `echo $$lang | sed -e 's/.*@//'`.sed 2>/dev/null > $$tmpdir/$$lang.new.po; then \ | |||
| if cmp $$lang.po $$tmpdir/$$lang.new.po >/dev/null 2>&1; then \ | |||
| rm -f $$tmpdir/$$lang.new.po; \ | |||
| else \ | |||
| if mv -f $$tmpdir/$$lang.new.po $$lang.po; then \ | |||
| :; \ | |||
| else \ | |||
| echo "creation of $$lang.po failed: cannot move $$tmpdir/$$lang.new.po to $$lang.po" 1>&2; \ | |||
| exit 1; \ | |||
| fi; \ | |||
| fi; \ | |||
| else \ | |||
| echo "creation of $$lang.po failed!" 1>&2; \ | |||
| rm -f $$tmpdir/$$lang.new.po; \ | |||
| fi | |||
| en@quot.insert-header: insert-header.sin | |||
| sed -e '/^#/d' -e 's/HEADER/en@quot.header/g' $(srcdir)/insert-header.sin > en@quot.insert-header | |||
| en@boldquot.insert-header: insert-header.sin | |||
| sed -e '/^#/d' -e 's/HEADER/en@boldquot.header/g' $(srcdir)/insert-header.sin > en@boldquot.insert-header | |||
| mostlyclean: mostlyclean-quot | |||
| mostlyclean-quot: | |||
| rm -f *.insert-header | |||
| @@ -0,0 +1,10 @@ | |||
| s/"\([^"]*\)"/“\1”/g | |||
| s/`\([^`']*\)'/‘\1’/g | |||
| s/ '\([^`']*\)' / ‘\1’ /g | |||
| s/ '\([^`']*\)'$/ ‘\1’/g | |||
| s/^'\([^`']*\)' /‘\1’ /g | |||
| s/“”/""/g | |||
| s/“/“[1m/g | |||
| s/”/[0m”/g | |||
| s/‘/‘[1m/g | |||
| s/’/[0m’/g | |||
| @@ -0,0 +1,25 @@ | |||
| # All this catalog "translates" are quotation characters. | |||
| # The msgids must be ASCII and therefore cannot contain real quotation | |||
| # characters, only substitutes like grave accent (0x60), apostrophe (0x27) | |||
| # and double quote (0x22). These substitutes look strange; see | |||
| # http://www.cl.cam.ac.uk/~mgk25/ucs/quotes.html | |||
| # | |||
| # This catalog translates grave accent (0x60) and apostrophe (0x27) to | |||
| # left single quotation mark (U+2018) and right single quotation mark (U+2019). | |||
| # It also translates pairs of apostrophe (0x27) to | |||
| # left single quotation mark (U+2018) and right single quotation mark (U+2019) | |||
| # and pairs of quotation mark (0x22) to | |||
| # left double quotation mark (U+201C) and right double quotation mark (U+201D). | |||
| # | |||
| # When output to an UTF-8 terminal, the quotation characters appear perfectly. | |||
| # When output to an ISO-8859-1 terminal, the single quotation marks are | |||
| # transliterated to apostrophes (by iconv in glibc 2.2 or newer) or to | |||
| # grave/acute accent (by libiconv), and the double quotation marks are | |||
| # transliterated to 0x22. | |||
| # When output to an ASCII terminal, the single quotation marks are | |||
| # transliterated to apostrophes, and the double quotation marks are | |||
| # transliterated to 0x22. | |||
| # | |||
| # This catalog furthermore displays the text between the quotation marks in | |||
| # bold face, assuming the VT100/XTerm escape sequences. | |||
| # | |||
| @@ -0,0 +1,22 @@ | |||
| # All this catalog "translates" are quotation characters. | |||
| # The msgids must be ASCII and therefore cannot contain real quotation | |||
| # characters, only substitutes like grave accent (0x60), apostrophe (0x27) | |||
| # and double quote (0x22). These substitutes look strange; see | |||
| # http://www.cl.cam.ac.uk/~mgk25/ucs/quotes.html | |||
| # | |||
| # This catalog translates grave accent (0x60) and apostrophe (0x27) to | |||
| # left single quotation mark (U+2018) and right single quotation mark (U+2019). | |||
| # It also translates pairs of apostrophe (0x27) to | |||
| # left single quotation mark (U+2018) and right single quotation mark (U+2019) | |||
| # and pairs of quotation mark (0x22) to | |||
| # left double quotation mark (U+201C) and right double quotation mark (U+201D). | |||
| # | |||
| # When output to an UTF-8 terminal, the quotation characters appear perfectly. | |||
| # When output to an ISO-8859-1 terminal, the single quotation marks are | |||
| # transliterated to apostrophes (by iconv in glibc 2.2 or newer) or to | |||
| # grave/acute accent (by libiconv), and the double quotation marks are | |||
| # transliterated to 0x22. | |||
| # When output to an ASCII terminal, the single quotation marks are | |||
| # transliterated to apostrophes, and the double quotation marks are | |||
| # transliterated to 0x22. | |||
| # | |||
| @@ -0,0 +1,256 @@ | |||
| # Finnish translations for TRE package. | |||
| # This file is distributed under the same license as the TRE package. | |||
| # | |||
| msgid "" | |||
| msgstr "" | |||
| "Project-Id-Version: TRE 0.7.4\n" | |||
| "Report-Msgid-Bugs-To: tre-general@lists.laurikari.net\n" | |||
| "POT-Creation-Date: 2009-09-18 15:41+0300\n" | |||
| "PO-Revision-Date: 2002-07-29 23:46+0300\n" | |||
| "Last-Translator: Ville Laurikari <vl@iki.fi>\n" | |||
| "Language-Team: Finnish <translation-team-fi@lists.sourceforge.net>\n" | |||
| "MIME-Version: 1.0\n" | |||
| "Content-Type: text/plain; charset=ISO-8859-1\n" | |||
| "Content-Transfer-Encoding: 8bit\n" | |||
| "Plural-Forms: nplurals=2; plural=(n != 1);\n" | |||
| #: lib/regerror.c:37 | |||
| msgid "No error" | |||
| msgstr "Ei virhettä" | |||
| #: lib/regerror.c:38 | |||
| msgid "No match" | |||
| msgstr "Hakulausekkeen esiintymää ei löytynyt" | |||
| #: lib/regerror.c:39 | |||
| msgid "Invalid regexp" | |||
| msgstr "Virheellinen lauseke" | |||
| #: lib/regerror.c:40 | |||
| msgid "Unknown collating element" | |||
| msgstr "Tuntematon lajittuva merkki" | |||
| #: lib/regerror.c:41 | |||
| msgid "Unknown character class name" | |||
| msgstr "Tuntematon merkkiluokka" | |||
| #: lib/regerror.c:42 | |||
| msgid "Trailing backslash" | |||
| msgstr "Lauseke loppuu kenoviivaan" | |||
| #: lib/regerror.c:43 | |||
| msgid "Invalid back reference" | |||
| msgstr "Virheellinen osalausekeviittaus" | |||
| #: lib/regerror.c:44 | |||
| msgid "Missing ']'" | |||
| msgstr "Puuttuva ']'" | |||
| #: lib/regerror.c:45 | |||
| msgid "Missing ')'" | |||
| msgstr "Puuttuva ')'" | |||
| #: lib/regerror.c:46 | |||
| msgid "Missing '}'" | |||
| msgstr "Puuttuva '}'" | |||
| #: lib/regerror.c:47 | |||
| msgid "Invalid contents of {}" | |||
| msgstr "Virhe {} sisällä" | |||
| #: lib/regerror.c:48 | |||
| msgid "Invalid character range" | |||
| msgstr "Virheellinen merkkialue" | |||
| #: lib/regerror.c:49 src/agrep.c:229 src/agrep.c:299 src/agrep.c:324 | |||
| #: src/agrep.c:695 src/agrep.c:734 | |||
| msgid "Out of memory" | |||
| msgstr "Muisti loppu" | |||
| #: lib/regerror.c:50 | |||
| msgid "Invalid use of repetition operators" | |||
| msgstr "Virheellinen toisto-operaattorin käyttö" | |||
| #: lib/regerror.c:65 | |||
| msgid "Unknown error" | |||
| msgstr "Tuntematon virhe" | |||
| #: src/agrep.c:96 src/agrep.c:103 | |||
| #, c-format | |||
| msgid "Usage: %s [OPTION]... PATTERN [FILE]...\n" | |||
| msgstr "Käyttö: %s [VALITSIN]... HAKULAUSEKE [TIEDOSTO]...\n" | |||
| #: src/agrep.c:98 | |||
| #, c-format | |||
| msgid "Try `%s --help' for more information.\n" | |||
| msgstr "Kokeile `%s --help' saadaksesi lisää tietoa.\n" | |||
| #: src/agrep.c:104 | |||
| #, c-format | |||
| msgid "" | |||
| "Searches for approximate matches of PATTERN in each FILE or standard input.\n" | |||
| "Example: `%s -2 optimize foo.txt' outputs all lines in file `foo.txt' that\n" | |||
| "match \"optimize\" within two errors. E.g. lines which contain \"optimise" | |||
| "\",\n" | |||
| "\"optmise\", and \"opitmize\" all match.\n" | |||
| msgstr "" | |||
| "Etsii hakulausekkeen likimääräisiä esiintymiä tiedostoista tai " | |||
| "vakiosyötteestä.\n" | |||
| "Esimerkki: `%s -2 lähteä foo.txt' palauttaa kaikki rivit tiedostossa\n" | |||
| "`foo.txt' joihin hakukaava \"lähteä\" sopii enintään kahdella virheellä.\n" | |||
| "Esimerkiksi rivit jotka sisältävät \"lähtee\" tai \"lähtö\" palautetaan.\n" | |||
| #: src/agrep.c:110 | |||
| #, c-format | |||
| msgid "" | |||
| "Regexp selection and interpretation:\n" | |||
| " -e, --regexp=PATTERN\t use PATTERN as a regular expression\n" | |||
| " -i, --ignore-case\t ignore case distinctions\n" | |||
| " -k, --literal\t\t PATTERN is a literal string\n" | |||
| " -w, --word-regexp\t force PATTERN to match only whole words\n" | |||
| "\n" | |||
| "Approximate matching settings:\n" | |||
| " -D, --delete-cost=NUM\t set cost of missing characters\n" | |||
| " -I, --insert-cost=NUM\t set cost of extra characters\n" | |||
| " -S, --substitute-cost=NUM set cost of wrong characters\n" | |||
| " -E, --max-errors=NUM\t select records that have at most NUM errors\n" | |||
| " -#\t\t\t select records that have at most # errors (# is a\n" | |||
| "\t\t\t digit between 0 and 9)\n" | |||
| "\n" | |||
| "Miscellaneous:\n" | |||
| " -d, --delimiter=PATTERN set the record delimiter regular expression\n" | |||
| " -v, --invert-match\t select non-matching records\n" | |||
| " -V, --version\t\t print version information and exit\n" | |||
| " -y, --nothing\t\t does nothing (for compatibility with the non-free\n" | |||
| "\t\t\t agrep program)\n" | |||
| " --help\t\t display this help and exit\n" | |||
| "\n" | |||
| "Output control:\n" | |||
| " -B, --best-match\t only output records with least errors\n" | |||
| " -c, --count\t\t only print a count of matching records per FILE\n" | |||
| " -h, --no-filename\t suppress the prefixing filename on output\n" | |||
| " -H, --with-filename\t print the filename for each match\n" | |||
| " -l, --files-with-matches only print FILE names containing matches\n" | |||
| " -M, --delimiter-after print record delimiter after record if -d is " | |||
| "used\n" | |||
| " -n, --record-number\t print record number with output\n" | |||
| " --line-number same as -n\n" | |||
| " -q, --quiet, --silent\t suppress all normal output\n" | |||
| " -s, --show-cost\t print match cost with output\n" | |||
| " --colour, --color use markers to distinguish the matching strings\n" | |||
| " --show-position prefix each output record with start and end\n" | |||
| " position of the first match within the record\n" | |||
| msgstr "" | |||
| "Hakulausekkeen valinta ja tulkinta:\n" | |||
| " -e, --regexp=HAKULAUSEKE käytä HAKULAUSEKEtta säännöllisenä lausekkeena\n" | |||
| " -i, --ignore-case älä erottele isoja ja pieniä kirjaimia\n" | |||
| " -k, --literal HAKULAUSEKE on kiinteä merkkijono\n" | |||
| " -w, --word-regexp anna hakulausekkeen sopia vain kokonaisiin " | |||
| "sanoihin\n" | |||
| "\n" | |||
| "Likimääräisen sovittamisen asetukset:\n" | |||
| " -D, --delete-cost=N aseta puuttuvien merkkien hinnaksi N\n" | |||
| " -I, --insert-cost=N aseta ylimääräisten merkkien hinnaksi N\n" | |||
| " -S, --substitute-cost=N aseta väärien merkkien hinnaksi N\n" | |||
| " -E, --max-errors=N valitse tietueet joissa on enintään N virhettä\n" | |||
| " -# valitse tietueet joissa on enintään # virhettä " | |||
| "(# on\n" | |||
| " kokonaisluku väliltä 0-9)\n" | |||
| "\n" | |||
| "Sekalaista:\n" | |||
| " -d, --delimiter=LAUSEKE aseta LAUSEKE tietueiden erotinlausekkeeksi\n" | |||
| " -v, --invert-match valitse tietueet jotka eivät sovi " | |||
| "hakulausekkeeseen\n" | |||
| " -V, --version tulosta versiotieto ja lopeta\n" | |||
| " -y, --nothing ei tee mitään (yhteensopivuudeksi ei-vapaan\n" | |||
| " agrep -ohjelman kanssa)\n" | |||
| " --help tulosta tämä ohje ja lopeta\n" | |||
| "\n" | |||
| "Tulostuksen asetukset:\n" | |||
| " -B, --best-match valitse tietueet joissa on vähiten virheitä\n" | |||
| " -c, --count tulosta vain sopivien tietueiden määrä per " | |||
| "TIEDOSTO\n" | |||
| " -h, --no-filename älä lisää tiedoston nimeä tietueen alkuun\n" | |||
| " -H, --with-filename lisää aina tiedoston nimi tietueen alkuun\n" | |||
| " -l, --files-with-matches tulosta vain niiden TIEDOSTOjen nimet, joissa " | |||
| "on\n" | |||
| " sopivia tietueita\n" | |||
| " -M, --delimiter-after tulosta erotin tietueen jälkeen jos -d on " | |||
| "käytössä\n" | |||
| " -n, --record-number tulosta tietuenumerot\n" | |||
| " --line-number sama kuin -n\n" | |||
| " -q, --quiet, --silent älä tulosta mitään\n" | |||
| " -s, --show-cost tulosta virheiden määrä\n" | |||
| " --colour, --color korosta tulostetuista tietueista osat jotka\n" | |||
| " sopivat hakulausekkeeseen\n" | |||
| " --show-position lisää tulostettujen tietueiden alkuun haku-\n" | |||
| " lausekkeeseen sopivan osamerkkijonon alku- ja\n" | |||
| " loppusijainti tietueessa\n" | |||
| #: src/agrep.c:149 | |||
| #, c-format | |||
| msgid "" | |||
| "With no FILE, or when FILE is -, reads standard input. If less than two\n" | |||
| "FILEs are given, -h is assumed. Exit status is 0 if a match is found, 1 " | |||
| "for\n" | |||
| "no match, and 2 if there were errors. If -E or -# is not specified, only\n" | |||
| "exact matches are selected.\n" | |||
| msgstr "" | |||
| "Jos TIEDOSTOja ei ole annettu, tai jos TIEDOSTO on -, luetaan " | |||
| "vakiosyötteestä.\n" | |||
| "Jos TIEDOSTOja on annettu vähemmän kuin kaksi, valitsin -h otetaan käyttöön\n" | |||
| "automaattisesti. Paluukoodi on 0 jos hakukaavan esiintymiä löytyi, 1 jos\n" | |||
| "niitä ei löytynyt ja 2 jos tapahtui virhe. Jos -E tai -# ei ole annettu,\n" | |||
| "vain tietueet jotka sopivat tarkasti hakulausekkeeseen valitaan.\n" | |||
| #: src/agrep.c:155 | |||
| #, c-format | |||
| msgid "" | |||
| "PATTERN is a POSIX extended regular expression (ERE) with the TRE " | |||
| "extensions.\n" | |||
| "See tre(7) for a complete description.\n" | |||
| msgstr "" | |||
| "HAKULAUSEKE on POSIXin määrittelemä laajennettu säännöllinen lauseke " | |||
| "(engl. \n" | |||
| "extended regular expression). Lisäksi voidaan käyttää TRE:n laajennuksia.\n" | |||
| "Hakulausekkeiden täysimittainen kuvaus on tre(7):ssä.\n" | |||
| #: src/agrep.c:159 | |||
| #, c-format | |||
| msgid "Report bugs to: " | |||
| msgstr "Raportoi virheistä osoitteeseen: " | |||
| #: src/agrep.c:244 | |||
| #, c-format | |||
| msgid "Error reading from %s: %s\n" | |||
| msgstr "Ei voi lukea kohteesta %s: %s\n" | |||
| #: src/agrep.c:339 | |||
| msgid "Cannot use -B when reading from standard input." | |||
| msgstr "Vakiosyötteestä luettaessa -B ei ole sallittu." | |||
| #: src/agrep.c:343 | |||
| msgid "(standard input)" | |||
| msgstr "(vakiosyöte)" | |||
| #: src/agrep.c:600 | |||
| #, c-format | |||
| msgid "Copyright (c) 2001-2009 Ville Laurikari <vl@iki.fi>.\n" | |||
| msgstr "Tekijänoikeus © 2001-2009 Ville Laurikari <vl@iki.fi>.\n" | |||
| #: src/agrep.c:622 | |||
| #, c-format | |||
| msgid "%s: invalid option --%s\n" | |||
| msgstr "%s: virheellinen valitsin --%s\n" | |||
| #: src/agrep.c:749 | |||
| msgid "Error in search pattern" | |||
| msgstr "Virhe hakulausekkeessa" | |||
| #: src/agrep.c:760 | |||
| msgid "Error in record delimiter pattern" | |||
| msgstr "Virhe tietueiden erotinlausekkeessa" | |||
| #: src/agrep.c:767 | |||
| msgid "Record delimiter pattern must not match an empty string" | |||
| msgstr "Tietueiden erotinlauseke ei saa sopia tyhjään merkkijonoon" | |||
| @@ -0,0 +1,23 @@ | |||
| # Sed script that inserts the file called HEADER before the header entry. | |||
| # | |||
| # At each occurrence of a line starting with "msgid ", we execute the following | |||
| # commands. At the first occurrence, insert the file. At the following | |||
| # occurrences, do nothing. The distinction between the first and the following | |||
| # occurrences is achieved by looking at the hold space. | |||
| /^msgid /{ | |||
| x | |||
| # Test if the hold space is empty. | |||
| s/m/m/ | |||
| ta | |||
| # Yes it was empty. First occurrence. Read the file. | |||
| r HEADER | |||
| # Output the file's contents by reading the next line. But don't lose the | |||
| # current line while doing this. | |||
| g | |||
| N | |||
| bb | |||
| :a | |||
| # The hold space was nonempty. Following occurrences. Do nothing. | |||
| x | |||
| :b | |||
| } | |||
| @@ -0,0 +1,6 @@ | |||
| s/"\([^"]*\)"/“\1”/g | |||
| s/`\([^`']*\)'/‘\1’/g | |||
| s/ '\([^`']*\)' / ‘\1’ /g | |||
| s/ '\([^`']*\)'$/ ‘\1’/g | |||
| s/^'\([^`']*\)' /‘\1’ /g | |||
| s/“”/""/g | |||
| @@ -0,0 +1,19 @@ | |||
| # Sed script that remove the POT-Creation-Date line in the header entry | |||
| # from a POT file. | |||
| # | |||
| # The distinction between the first and the following occurrences of the | |||
| # pattern is achieved by looking at the hold space. | |||
| /^"POT-Creation-Date: .*"$/{ | |||
| x | |||
| # Test if the hold space is empty. | |||
| s/P/P/ | |||
| ta | |||
| # Yes it was empty. First occurrence. Remove the line. | |||
| g | |||
| d | |||
| bb | |||
| :a | |||
| # The hold space was nonempty. Following occurrences. Do nothing. | |||
| x | |||
| :b | |||
| } | |||