Changeset 31 in dev for BasicCompiler_Common


Ignore:
Timestamp:
Jan 13, 2007, 4:26:50 AM (18 years ago)
Author:
dai_9181
Message:

_System_LocalThis(見えないThisポインタパラメータ)を通常のパラメータ保有領域ではなく、リアルパラメータ保有領域に移動した。
メソッドとグローバル関数のオーバーロードに対応(DLL関数オーバーロードには未対応)。

Location:
BasicCompiler_Common
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • BasicCompiler_Common/Class.cpp

    r29 r31  
    698698
    699699        //標準コンストラクタ(引数なし)
    700         if(psi->ParmNum==1) fConstructor=1;
     700        if(psi->ParmNum==0) fConstructor=1;
    701701
    702702        //コピーコンストラクタ
    703         if(psi->ParmNum==2){
     703        if(psi->ParmNum==1){
    704704            if(psi->pParmInfo[1].type==DEF_OBJECT&&
    705705                psi->pParmInfo[1].u.pobj_c==pobj_c) fConstructor=2;
  • BasicCompiler_Common/NumOpe_GetType.cpp

    r11 r31  
    205205    /////////////////////////////////////////////
    206206
    207     PARAMETER_INFO *ppi;
     207
     208    //_System_LocalThis
     209    PARAMETER_INFO *ppi = (PARAMETER_INFO *)HeapAlloc(hHeap,0,sizeof(PARAMETER_INFO)*3);
    208210    int iParmNum=0;
    209 
    210     //_System_LocalThis
    211     ppi=(PARAMETER_INFO *)HeapAlloc(hHeap,0,sizeof(PARAMETER_INFO)*3);
    212     ppi[iParmNum].bArray=0;
    213     ppi[iParmNum].bByVal=0;
    214     ppi[iParmNum].name=0;
    215     ppi[iParmNum].type=DEF_PTR_VOID;
    216     ppi[iParmNum].u.index=-1;
    217     ppi[iParmNum].SubScripts[0]=-1;
    218     iParmNum++;
    219211
    220212    if(bTwoTerm){
  • BasicCompiler_Common/Object.cpp

    r29 r31  
    226226            i5=pVar[i3].u.pobj_c->DestructorMemberSubIndex;
    227227            if(i5!=-1)
    228                 Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,0,pVar[i3].name,DEF_OBJECT);
     228                Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,pVar[i3].name,DEF_OBJECT);
    229229
    230230            //メモリを解放する
     
    289289                        }
    290290                        lstrcat(temporary,"]");
    291                         Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,0,temporary,DEF_OBJECT);
     291                        Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,temporary,DEF_OBJECT);
    292292
    293293                        ss[0]++;
     
    303303                }
    304304                else{
    305                     Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,0,pVar[i3].name,DEF_OBJECT);
     305                    Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,pVar[i3].name,DEF_OBJECT);
    306306                }
    307307            }
     
    313313        i3=pVar[indexSystemGC].u.pobj_c->DestructorMemberSubIndex;
    314314        if(i3!=-1){
    315             Opcode_CallProc("",pVar[indexSystemGC].u.pobj_c->ppobj_Method[i3]->psi,0,0,pVar[indexSystemGC].name,DEF_OBJECT);
    316         }
    317     }
    318 }
    319 
     315            Opcode_CallProc("",pVar[indexSystemGC].u.pobj_c->ppobj_Method[i3]->psi,0,pVar[indexSystemGC].name,DEF_OBJECT);
     316        }
     317    }
     318}
     319
  • BasicCompiler_Common/Overload.cpp

    r28 r31  
    3030    }
    3131
    32     char temporary[VN_SIZE];
    33     if((ObjectName[0]||ppsi[0]->pobj_ParentClass) && isStatic == false ){
    34         //Thisポインタ(第一パラメータ)のダミーを作成
    35         if(Parameter[0]) sprintf(temporary,"0%c%cVoidPtr,%s",1,ESC_AS,Parameter);
    36         else sprintf(temporary,"0%c%cVoidPtr",1,ESC_AS);
    37     }
    38     else lstrcpy(temporary,Parameter);
    39 
    4032    //パラメータオブジェクトを生成
    41     pobj_parameter=new CParameter(temporary);
     33    pobj_parameter=new CParameter(Parameter);
    4234    if(pReturnTypeInfo) pobj_parameter->SetReturnType(pReturnTypeInfo);
    4335
  • BasicCompiler_Common/StrOperation.cpp

    r15 r31  
    704704    return 0;
    705705}
     706
     707void ShortPathToLongPath(const char *ShortPath,char *LongPath){
     708    HANDLE hFind;
     709    WIN32_FIND_DATA wfd;
     710    int i;
     711    char dummy[MAX_PATH];
     712    for(i=0;i<MAX_PATH;i++){
     713        LongPath[i]=ShortPath[i];
     714        if((ShortPath[i-1]==':'&&ShortPath[i]=='\\')||(ShortPath[i-1]=='\\'&&ShortPath[i]=='\\')){
     715            LongPath[i+1]=0;
     716            break;
     717        }
     718    }
     719    if(ShortPath[i-1]=='\\'&&ShortPath[i]=='\\'){
     720        for(i++;i<MAX_PATH;i++){
     721            if(IsDBCSLeadByte(ShortPath[i])){
     722                i++;
     723                continue;
     724            }
     725            LongPath[i]=ShortPath[i];
     726            if(ShortPath[i]=='\\'){
     727                LongPath[i+1]=0;
     728                break;
     729            }
     730        }
     731        for(i++;i<MAX_PATH;i++){
     732            if(IsDBCSLeadByte(ShortPath[i])){
     733                i++;
     734                continue;
     735            }
     736            LongPath[i]=ShortPath[i];
     737            if(ShortPath[i]=='\\'){
     738                LongPath[i+1]=0;
     739                break;
     740            }
     741        }
     742    }
     743    for(i++;i<MAX_PATH;i++){
     744        if(IsDBCSLeadByte(ShortPath[i])){
     745            i++;
     746            continue;
     747        }
     748        if(ShortPath[i]=='\\'||ShortPath[i]=='\0'){
     749            strncpy(dummy,ShortPath,i);
     750            dummy[i]=0;
     751            if((hFind=FindFirstFile(dummy,&wfd))!=INVALID_HANDLE_VALUE) FindClose(hFind);
     752            lstrcat(LongPath,wfd.cFileName);
     753
     754            if(ShortPath[i]=='\0') break;
     755            lstrcat(LongPath,"\\");
     756
     757            if(ShortPath[i]=='\\'&&ShortPath[i+1]=='\0'){
     758                break;
     759            }
     760        }
     761    }
     762}
  • BasicCompiler_Common/Subroutine.cpp

    r30 r31  
    717717    psi->ParmNum=0;
    718718
    719     if(pobj_c&&bStatic==0){
    720         //オブジェクトメンバの場合は、第一パラメータをThisポインタ引き渡し用として利用
    721         psi->pParmInfo[psi->ParmNum].name=(char *)HeapAlloc(hHeap,0,lstrlen("_System_LocalThis")+1);
    722         lstrcpy(psi->pParmInfo[psi->ParmNum].name,"_System_LocalThis");
    723         psi->pParmInfo[psi->ParmNum].type=DEF_PTR_VOID;
    724         psi->pParmInfo[psi->ParmNum].u.index=-1;
    725         psi->pParmInfo[psi->ParmNum].bByVal=1;
    726         psi->pParmInfo[psi->ParmNum].bArray=0;
    727         psi->pParmInfo[psi->ParmNum].SubScripts[0]=-1;
    728 
    729         psi->ParmNum++;
    730     }
    731 
    732719    //パラメータ
    733720    if(buffer[i]!='('){
     
    1008995    }
    1009996
     997    //リアルパラメータ領域を取得(_System_LocalThis、_System_ReturnValueを考慮して2つだけ多く確保する)
     998    psi->pRealParmInfo=(PARAMETER_INFO *)HeapAlloc(hHeap,0,(psi->ParmNum+2)*sizeof(PARAMETER_INFO));
     999    psi->RealParmNum=0;
     1000
     1001    if(pobj_c&&bStatic==0){
     1002        i = psi->RealParmNum;
     1003
     1004        //オブジェクトメンバの場合は、第一パラメータを_System_LocalThis引き渡し用として利用
     1005        psi->pRealParmInfo[i].name = "_System_LocalThis";
     1006        psi->pRealParmInfo[i].type=DEF_PTR_VOID;
     1007        psi->pRealParmInfo[i].u.index=-1;
     1008        psi->pRealParmInfo[i].bByVal=1;
     1009        psi->pRealParmInfo[i].bArray=0;
     1010        psi->pRealParmInfo[i].SubScripts[0]=-1;
     1011
     1012        psi->RealParmNum++;
     1013    }
     1014
    10101015    if(psi->ReturnType==DEF_OBJECT){
    1011         //オブジェクト インスタンスを戻り値として持つ場合
     1016        i = psi->RealParmNum;
     1017
     1018        //実体オブジェクトを戻り値として持つ場合
    10121019        //※第一パラメータ(Thisポインタありの場合は第二パラメータ)を戻り値用の参照宣言にする
    1013 
    1014         psi->RealParmNum=psi->ParmNum+1;
    1015         psi->RealSecondParmNum=psi->SecondParmNum+1;
    1016 
    1017         psi->pRealParmInfo=(PARAMETER_INFO *)HeapAlloc(hHeap,0,(psi->RealParmNum+1)*sizeof(PARAMETER_INFO));
    1018 
    1019         i=0;
    1020         if(pobj_c&&bStatic==0){
    1021             psi->pRealParmInfo[0]=psi->pParmInfo[0];
    1022             i++;
    1023         }
    10241020
    10251021        if(psi->name[0]==1&&psi->name[1]==ESC_OPERATOR)
     
    10311027        psi->pRealParmInfo[i].bArray=0;
    10321028        psi->pRealParmInfo[i].SubScripts[0]=-1;
    1033         i++;
    1034 
    1035         for(;i<psi->RealParmNum;i++){
    1036             psi->pRealParmInfo[i]=psi->pParmInfo[i-1];
    1037         }
    1038     }
    1039     else{
    1040         psi->pRealParmInfo=psi->pParmInfo;
    1041         psi->RealParmNum=psi->ParmNum;
    1042         psi->RealSecondParmNum=psi->SecondParmNum;
     1029       
     1030        psi->RealParmNum++;
     1031    }
     1032
     1033    //パラメータをコピー
     1034    for( i = 0; i < psi->ParmNum; i++, psi->RealParmNum++ ){
     1035        psi->pRealParmInfo[psi->RealParmNum]=psi->pParmInfo[i];
    10431036    }
    10441037
     
    11911184        HeapDefaultFree(psi->pParmInfo[i2].name);
    11921185    }
    1193     if(psi->pRealParmInfo!=psi->pParmInfo) HeapDefaultFree(psi->pRealParmInfo);
     1186    HeapDefaultFree(psi->pRealParmInfo);
    11941187    if(psi->pParmInfo) HeapDefaultFree(psi->pParmInfo);
    11951188    psi->pRealParmInfo=0;
  • BasicCompiler_Common/common.h

    r29 r31  
    516516void GetCalcName(int idCalc,char *name);
    517517BOOL IsFile(char *path);
     518BOOL ShortPathToLongPath(char ShortPath[MAX_PATH],char *LongPath);
    518519BOOL GetFolder(HWND hWnd,char *folder,char *OpenFolderTitle);
     520void ShortPathToLongPath(const char *ShortPath,char *LongPath);
    519521
    520522//calculation.cpp
  • BasicCompiler_Common/hash.cpp

    r28 r31  
    146146        }
    147147    }
    148 
    149     if(pobj_CompilingClass){
    150         //自身のオブジェクトのメンバ関数を検索
    151 
    152 
    153         //////////////////////////////////////////////
    154         // 静的メソッド
    155         //////////////////////////////////////////////
    156 
    157         CClass *pobj_c = pobj_CompilingClass;
    158 
    159         for(i=0;i<pobj_c->iStaticMethodNum;i++){
    160             if(lstrcmp(name,pobj_c->ppobj_StaticMethod[i]->psi->name)==0){
    161                 ppArray_si[num]=pobj_c->ppobj_StaticMethod[i]->psi;
    162                 num++;
    163             }
    164         }
    165 
    166 
    167         ///////////////////////
    168         // 動的メソッド(一般)
    169         ///////////////////////
    170         for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
    171             //オーバーライドされた関数を飛び越す
    172             if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass==0) break;
    173         }
    174         for(;i<pobj_CompilingClass->iMethodNum;i++){
    175             if(lstrcmp(name,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
    176                 ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
    177                 num++;
    178             }
    179         }
    180 
    181         //オーバーライドされたメンバ関数
    182         for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
    183             //オーバーライドされた関数を飛び越す
    184             if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass){
     148    else{
     149        //オブジェクトが明示的に指定されていないとき
     150
     151        if(pobj_CompilingClass){
     152            //自身のオブジェクトのメンバ関数を検索
     153
     154
     155            //////////////////////////////////////////////
     156            // 静的メソッド
     157            //////////////////////////////////////////////
     158
     159            CClass *pobj_c = pobj_CompilingClass;
     160
     161            for(i=0;i<pobj_c->iStaticMethodNum;i++){
     162                if(lstrcmp(name,pobj_c->ppobj_StaticMethod[i]->psi->name)==0){
     163                    ppArray_si[num]=pobj_c->ppobj_StaticMethod[i]->psi;
     164                    num++;
     165                }
     166            }
     167
     168
     169            ///////////////////////
     170            // 動的メソッド(一般)
     171            ///////////////////////
     172            for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
     173                //オーバーライドされた関数を飛び越す
     174                if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass==0) break;
     175            }
     176            for(;i<pobj_CompilingClass->iMethodNum;i++){
    185177                if(lstrcmp(name,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
    186178                    ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
     
    188180                }
    189181            }
    190         }
    191     }
    192 
    193     if(num) goto finish;
    194 
    195 
    196     //ハッシュ値を取得
    197     int key;
    198     key=hash_default(name);
    199 
    200     //格納位置を取得
    201     extern SUBINFO **ppSubHash;
    202     SUBINFO *psi;
    203     psi=ppSubHash[key];
    204     while(psi){
    205         if(!psi->pobj_ParentClass){
    206             if(lstrcmp(psi->name,name)==0){
    207                 ppArray_si[num]=psi;
    208                 num++;
    209             }
    210         }
    211 
    212         psi=psi->pNextData;
    213     }
    214 
     182
     183            //オーバーライドされたメンバ関数
     184            for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
     185                //オーバーライドされた関数を飛び越す
     186                if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass){
     187                    if(lstrcmp(name,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
     188                        ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
     189                        num++;
     190                    }
     191                }
     192            }
     193        }
     194
     195
     196        ///////////////////////////
     197        // グローバル関数を検索
     198        ///////////////////////////
     199
     200        //ハッシュ値を取得
     201        int key;
     202        key=hash_default(name);
     203
     204        //格納位置を取得
     205        extern SUBINFO **ppSubHash;
     206        SUBINFO *psi;
     207        psi=ppSubHash[key];
     208        while(psi){
     209            if(!psi->pobj_ParentClass){
     210                if(lstrcmp(psi->name,name)==0){
     211                    ppArray_si[num]=psi;
     212                    num++;
     213                }
     214            }
     215
     216            psi=psi->pNextData;
     217        }
     218
     219    }
    215220finish:
    216221
  • BasicCompiler_Common/preprocessor.cpp

    r15 r31  
    88
    99
     10
     11//////////////////////////////////////
     12// #requireの管理
     13//////////////////////////////////////
     14class CRequireFiles{
     15    char **ppFilePath;
     16    int count;
     17public:
     18    CRequireFiles(){
     19        ppFilePath = (char **)malloc( 1 );
     20        count = 0;
     21    }
     22    ~CRequireFiles(){
     23        for( int i = 0; i < count; i++ ){
     24            free( ppFilePath[i] );
     25        }
     26        free( ppFilePath );
     27    }
     28    bool IsIncluded( const char *FilePath ){
     29        for( int i = 0; i < count; i++ ){
     30            if( lstrcmpi( ppFilePath[i], FilePath ) == 0 ){
     31                return true;
     32            }
     33        }
     34        return false;
     35    }
     36    void Add( const char *FilePath ){
     37        //既に読み込まれているとき
     38        if( IsIncluded( FilePath ) ) return;
     39
     40        //追加
     41        ppFilePath = (char **)realloc(ppFilePath, ( count + 1 ) * sizeof(char *) );
     42        ppFilePath[count] = (char *)malloc( lstrlen(FilePath) + 1 );
     43        lstrcpy( ppFilePath[count], FilePath );
     44        count++;
     45    }
     46};
     47CRequireFiles *pRequireFiles;
     48
     49
     50//////////////////////////////////////
     51// #define間するクラス
     52//////////////////////////////////////
    1053class CDefine{
    1154    int num;
     
    317360    int i,i2,i3,sw1,FileSize,LineNum,FileLayer[255],layer,LastFileByte[255];
    318361    char *buffer,temporary[MAX_PATH],temp2[MAX_PATH+255],*LayerDir[255];
    319     DWORD AccBytes;
    320     HANDLE hFile;
    321362
    322363    IncludeFileInfo.ppFileNames=(char **)HeapAlloc(hHeap,HEAP_ZERO_MEMORY,sizeof(char *));
     
    350391        }
    351392        if(buffer[i-1]=='\n'&&buffer[i]=='#'){
    352             if(memcmp(buffer+i+1,"include",7)==0){
    353                 i2=i+8;
    354                 while(buffer[i2]==' '||buffer[i2]=='\t') i2++;
    355 
    356                 if(buffer[i2]=='\"') sw1=0;
    357                 else if(buffer[i2]=='<') sw1=1;
    358                 i2++;
    359 
    360                 for(i3=0;;i2++,i3++){
    361                     if((buffer[i2]=='\"'&&sw1==0)||(buffer[i2]=='>'&&sw1==1)||buffer[i2]=='\n'||buffer[i2]=='\0'){
    362                         temporary[i3]=0;
    363                         break;
    364                     }
    365                     temporary[i3]=buffer[i2];
    366                 }
    367                 while(buffer[i2]!='\n'&&buffer[i2]!='\0') i2++;
    368 
    369                 if(sw1){
    370                     sprintf(temp2,"%s%s",szIncludeDir,temporary);
    371                     lstrcpy(temporary,temp2);
    372                 }
    373                 else GetFullPath(temporary,LayerDir[layer]);
     393            bool isRequire = false;
     394            if(memcmp( buffer + i + 1, "include", 7 ) == 0
     395                || memcmp( buffer + i + 1, "require", 7 ) == 0){
     396
     397                    //#requireの場合
     398                    if( buffer[i + 1] == 'r' ) isRequire = true;
     399
     400                    i2=i+8;
     401                    while(buffer[i2]==' '||buffer[i2]=='\t') i2++;
     402
     403                    if(buffer[i2]=='\"') sw1=0;
     404                    else if(buffer[i2]=='<') sw1=1;
     405                    i2++;
     406
     407                    for(i3=0;;i2++,i3++){
     408                        if((buffer[i2]=='\"'&&sw1==0)||(buffer[i2]=='>'&&sw1==1)||buffer[i2]=='\n'||buffer[i2]=='\0'){
     409                            temporary[i3]=0;
     410                            break;
     411                        }
     412                        temporary[i3]=buffer[i2];
     413                    }
     414                    while(buffer[i2]!='\n'&&buffer[i2]!='\0') i2++;
     415
     416                    if(sw1){
     417                        sprintf(temp2,"%s%s",szIncludeDir,temporary);
     418                        lstrcpy(temporary,temp2);
     419                    }
     420                    else GetFullPath(temporary,LayerDir[layer]);
    374421            }
    375422            else if(memcmp(buffer+i+1,"prompt",6)==0){
     
    406453            IncludeFileInfo.FilesNum++;
    407454
    408             //インクルードファイルを読み込む
    409             hFile=CreateFile(temporary,GENERIC_READ,0,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
    410             if(hFile==INVALID_HANDLE_VALUE){
    411                 sprintf(temp2,"インクルードファイル \"%s\" をオープンできません",temporary);
    412                 extern char *basbuf;
    413                 basbuf=base+2;
    414                 SetError(-1,temp2,i);
    415                 break;
    416             }
    417             FileSize=GetFileSize(hFile,NULL);
    418 
    419             //読み込み
     455            //#requireの場合では、既に読み込まれているファイルは読み込まないようにする
     456            bool isFake = false;
     457            if( isRequire ){
     458                if( pRequireFiles->IsIncluded( temporary ) ){
     459                    //既に読み込まれているとき
     460                    isFake = true;
     461                }
     462            }
     463
    420464            char *temp3;
    421             temp3=(char *)HeapAlloc(hHeap,0,FileSize+1);
    422             ReadFile(hFile,temp3,FileSize,&AccBytes,NULL);
    423             temp3[AccBytes]=0;
    424 
    425             //CRLFをLFに変換
    426             ChangeReturnCode(temp3);
    427 
    428             //コメント削除
    429             DeleteComment(temp3);
    430 
    431             //#ifdefディレクティブ
    432             DirectiveIfdef(temp3);
    433 
    434             FileSize=lstrlen(temp3);
     465            if( isFake ){
     466                //既に読み込まれているときは空データを生成
     467                temp3 = (char *)HeapAlloc(hHeap,HEAP_ZERO_MEMORY,1);;
     468                FileSize = 0;
     469            }
     470            else{
     471                //取り込まれたファイルを収集する
     472                pRequireFiles->Add( temporary );
     473
     474                //インクルードファイルを読み込む
     475                DWORD AccBytes;
     476                HANDLE hFile=CreateFile(temporary,GENERIC_READ,0,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
     477                if(hFile==INVALID_HANDLE_VALUE){
     478                    sprintf(temp2,"インクルードファイル \"%s\" をオープンできません",temporary);
     479                    extern char *basbuf;
     480                    basbuf=base+2;
     481                    SetError(-1,temp2,i);
     482                    break;
     483                }
     484                FileSize=GetFileSize(hFile,NULL);
     485
     486                //読み込み
     487                temp3=(char *)HeapAlloc(hHeap,0,FileSize+1);
     488                ReadFile(hFile,temp3,FileSize,&AccBytes,NULL);
     489                temp3[AccBytes]=0;
     490                CloseHandle(hFile);
     491
     492                //CRLFをLFに変換
     493                ChangeReturnCode(temp3);
     494
     495                //コメント削除
     496                DeleteComment(temp3);
     497
     498                //#ifdefディレクティブ
     499                DirectiveIfdef(temp3);
     500
     501                FileSize=lstrlen(temp3);
     502            }
    435503
    436504            i3=lstrlen(buffer)+FileSize;
     
    441509
    442510            //クローズ
    443             CloseHandle(hFile);
    444511            HeapDefaultFree(temp3);
    445512
     
    505572
    506573    //インクルードファイルを読み込む
     574    pRequireFiles = new CRequireFiles();
    507575    base=IncludeFiles(base);
     576    delete pRequireFiles;
    508577
    509578    //#define情報を破棄
Note: See TracChangeset for help on using the changeset viewer.