DIRECTORY BasicTime USING [GMT, Period], Commander, CommanderOps, FS USING [ComponentPositions, Error, ExpandName, FileInfo, StreamOpen], IO, MakeDo, Rope, TextFind; MakeItDepsImpl: CEDAR PROGRAM IMPORTS BasicTime, Commander, CommanderOps, FS, IO, MakeDo, Rope, TextFind = BEGIN ROPE: TYPE ~ Rope.ROPE; RopeList: TYPE ~ LIST OF ROPE; PatternList: TYPE ~ LIST OF PatternRule; PatternRule: TYPE ~ REF PatternRulePrivate; PatternRulePrivate: TYPE ~ RECORD [ resultTarget: TextFind.Target, fromPats: RopeList, cmdPat: ROPE]; PatternInstance: TYPE ~ REF PatternInstancePrivate; PatternInstancePrivate: TYPE ~ RECORD [ rule: PatternRule, from: MakeDo.From, cmd: ROPE]; MakeItData: TYPE ~ RECORD [ makeItFull, makeItShort, resultDir: ROPE ]; patternClass: MakeDo.ActionClass ¬ NEW[MakeDo.ActionClassRep ¬ [ CheckConsistency: CheckConsistencyByDates, Rederive: RederivePattern ]]; makeItClass: MakeDo.ActionClass ¬ NEW[MakeDo.ActionClassRep ¬ [ CheckConsistency: CheckConsistencyByDates, Rederive: RederiveMakeIt ]]; pats: PatternList ¬ NIL; PatternFind: PROC [resultName: ROPE, finderData: REF ANY] RETURNS [found: BOOLEAN, sought: MakeDo.Node, makes: MakeDo.NodeList, cmdFrom: MakeDo.NodeList, from: MakeDo.From, cmd: ROPE, class: MakeDo.ActionClass, foundData: REF ANY] --MakeDo.FinderProc-- = { makeItData: REF MakeItData; fullFName, resultDir: ROPE; cp: FS.ComponentPositions; dirOmitted: BOOL; [fullFName, cp, dirOmitted] ¬ FS.ExpandName[name: resultName ! FS.Error => GOTO Fail]; resultName ¬ fullFName; resultDir ¬ fullFName.Substr[len: cp.base.start]; FOR pl: PatternList ¬ pats, pl.rest WHILE pl#NIL DO pat: PatternRule ~ pl.first; matchStart, matchEnd, selStart, selEnd: INT; subs: TextFind.Subs; [found, matchStart, matchEnd, selStart, selEnd, subs] ¬ TextFind.RopeSearch[direction: forward, target: pat.resultTarget, rope: resultName, all: TRUE]; IF found THEN { from ¬ [NIL, NIL]; FOR rl: RopeList ¬ pat.fromPats, rl.rest WHILE rl#NIL DO fromName: ROPE ~ TextFind.RopeReplace[rope: resultName, with: rl.first, pattern: TRUE, subs: subs]; fromNode: MakeDo.Node ¬ MakeDo.GetNode[someName: fromName, class: MakeDo.fileClass]; from.mustHave ¬ CONS[fromNode, from.mustHave]; ENDLOOP; cmdFrom ¬ NIL; makes ¬ LIST[sought ¬ MakeDo.GetNode[someName: resultName, class: MakeDo.fileClass]]; cmd ¬ Rope.Cat["From ", resultDir, " ", TextFind.RopeReplace[rope: resultName, with: pat.cmdPat, pattern: TRUE, subs: subs] ]; class ¬ patternClass; foundData ¬ NEW [PatternInstancePrivate ¬ [pat, from, cmd]]; RETURN}; ENDLOOP; found ¬ FALSE; sought ¬ NIL; EXITS Fail => {found ¬ FALSE; sought ¬ NIL}; }; MakeItFind: PROC [resultName: ROPE, finderData: REF ANY] RETURNS [found: BOOLEAN, sought: MakeDo.Node, makes: MakeDo.NodeList, cmdFrom: MakeDo.NodeList, from: MakeDo.From, cmd: ROPE, class: MakeDo.ActionClass, foundData: REF ANY] --MakeDo.FinderProc-- = { makeItData: REF MakeItData; fullFName, resultDir, resultShort, makeItFull, makeItShort: ROPE; cp: FS.ComponentPositions; dirOmitted: BOOL; [fullFName, cp, dirOmitted] ¬ FS.ExpandName[name: resultName ! FS.Error => GOTO Fail]; resultName ¬ fullFName; resultShort ¬ fullFName.Substr[start: cp.base.start]; resultDir ¬ fullFName.Substr[len: cp.base.start]; [] ¬ FS.FileInfo[name: Rope.Concat[resultName, ".MakeIt"] ! FS.Error => GOTO Fail]; makeItShort ¬ resultShort.Concat[".MakeIt"]; makeItFull ¬ resultDir.Concat[makeItShort]; foundData ¬ makeItData ¬ NEW[MakeItData ¬ [ makeItFull: makeItFull, makeItShort: makeItShort, resultDir: resultDir ]]; from ¬ DeriveFrom[makeItData]; cmdFrom ¬ LIST[MakeDo.GetNode[someName: makeItFull, class: MakeDo.fileClass]]; makes ¬ LIST[sought ¬ MakeDo.GetNode[someName: resultName, class: MakeDo.fileClass]]; cmd ¬ DeriveCmd[makeItData]; class ¬ makeItClass; found ¬ TRUE; EXITS Fail => { found ¬ FALSE; sought ¬ NIL; }; }; WithoutVersion: PROC [with: ROPE] RETURNS [without: ROPE] ~ { cp: FS.ComponentPositions; [fullFName: without, cp: cp] ¬ FS.ExpandName[name: with]; without ¬ Rope.Substr[base: without, len: cp.ext.start+cp.ext.length]; }; DeriveCmd: PROC [makeItData: REF MakeItData] RETURNS [cmd: ROPE] ~ {RETURN [IO.PutFR["From %g Source %g", [rope[makeItData.resultDir]], [rope[makeItData.makeItShort]] ]]}; DeriveFrom: PROC [makeItData: REF MakeItData] RETURNS [from: MakeDo.From] ~ { s: IO.STREAM ¬ FS.StreamOpen[fileName: makeItData.makeItFull]; line: ROPE; from ¬ [mustHave: LIST[MakeDo.GetNode[someName: FS.ExpandName[name: makeItData.makeItFull].fullFName, class: MakeDo.fileClass]], optional: NIL]; UNTIL Rope.Match[pattern: "--*{*}*", object: line ¬ IO.GetLineRope[s ! IO.EndOfStream => GOTO NotDependentOnAnything]] DO ENDLOOP; IO.Close[self: s]; line ¬ Rope.Substr[base: line, start: Rope.Find[s1: line, s2: "{"]+1]; --Strip thru "{" line ¬ Rope.Substr[base: line, len: Rope.Find[s1: line, s2: "}"]]; -- Strip "}", etc. s ¬ IO.RIS[rope: line]; DO token: ROPE ~ FS.ExpandName[IO.GetTokenRope[stream: s, breakProc: IO.IDProc ! IO.EndOfStream => EXIT].token, makeItData.resultDir].fullFName; from.mustHave ¬ CONS[MakeDo.GetNode[someName: token, class: MakeDo.fileClass], from.mustHave]; ENDLOOP; IO.Close[self: s]; EXITS NotDependentOnAnything => {}; }; ForceConsistencyReturn: ERROR [setConsistent: BOOL, setReason: ROPE] ~ CODE; CheckConsistencyByDates: PROC [a: MakeDo.Action, result: MakeDo.Node] RETURNS [consistent: BOOL, reason: ROPE] --MakeDo.ConsistencyChecker-- = { ingredientFound: BOOL ¬ FALSE; PerIngredient: PROC [n: MakeDo.Node, which: MakeDo.ActionDep, optional: BOOL] ~ { nodeTime: BasicTime.GMT ¬ MakeDo.InnerGetCreated[n]; IF nodeTime=MakeDo.notExistTime THEN RETURN; ingredientFound ¬ TRUE; IF resultExists AND BasicTime.Period[from: nodeTime, to: resultTime] < 0 THEN ERROR ForceConsistencyReturn[setConsistent: FALSE, setReason: IO.PutFLR["result %g (of %g) predates ingredient %g (of %g)", LIST[[rope[resultName]], [time[resultTime]], [rope[MakeDo.PublicPartsOfNode[n: n].name]], [time[nodeTime]]]]]; RETURN}; resultTime: MakeDo.Time = result.InnerGetCreated[]; resultName: ROPE = MakeDo.PublicPartsOfNode[n: result].name; resultExists: BOOL ~ resultTime # MakeDo.notExistTime; MakeDo.InnerEnumerateSources[a: a, which: data, to: PerIngredient ! ForceConsistencyReturn => { consistent ¬ setConsistent; reason ¬ setReason; GOTO Exit; }]; IF NOT ingredientFound THEN RETURN [TRUE, "no inputs exist to indicate inconsistency"]; IF NOT resultExists THEN RETURN [FALSE, "some inputs but no output exist"]; RETURN [consistent: TRUE, reason: "result dated later than any existing ingredient"]; EXITS Exit => a ¬ a}; RederiveMakeIt: PROC [a: MakeDo.Action] RETURNS [from: MakeDo.From, cmd: ROPE] --MakeDo.RederiveProc-- = { makeItData: REF MakeItData ~ NARROW[MakeDo.PublicPartsOfAction[a].foundData]; from ¬ DeriveFrom[makeItData]; cmd ¬ DeriveCmd[makeItData]; }; RederivePattern: PROC [a: MakeDo.Action] RETURNS [from: MakeDo.From, cmd: ROPE] --MakeDo.RederiveProc-- = { pi: PatternInstance ~ NARROW[MakeDo.PublicPartsOfAction[a].foundData]; RETURN [pi.from, pi.cmd]}; AddPattern: PROC [resultPat: ROPE, froms: RopeList, cmdPat: ROPE] ~ { pats ¬ CONS[NEW[PatternRulePrivate ¬ [TextFind.TargetFromRope[rope: resultPat, pattern: TRUE], froms, cmdPat]], pats]; RETURN}; TestFind: PROC [cmd: Commander.Handle] RETURNS [result: REF ANY, msg: ROPE] --Commander.CommandProc-- ~ { argv: CommanderOps.ArgumentVector ~ CommanderOps.Parse[cmd]; IF argv.argc<3 THEN RETURN [$Failure, "Usage: target seek (forward|backward|(+|-)(case|word|def|all))* [with]"]; {target: TextFind.Target ~ TextFind.TargetFromRope[rope: argv[1], pattern: TRUE]; subject: ROPE ~ argv[2]; direction: TextFind.Direction ¬ forward; case: BOOL ¬ TRUE; word, def, all, found: BOOL ¬ FALSE; with: ROPE ¬ NIL; matchStart, matchEnd, selStart, selEnd: INT; subs: TextFind.Subs; FOR i: INT IN (2 .. argv.argc) DO SELECT TRUE FROM argv[i].Equal["forward"] => direction ¬ forward; argv[i].Equal["backward"] => direction ¬ backward; argv[i].Equal["-case"] => case ¬ FALSE; argv[i].Equal["-word"] => word ¬ FALSE; argv[i].Equal["-def"] => def ¬ FALSE; argv[i].Equal["-all"] => all ¬ FALSE; argv[i].Equal["+case"] => case ¬ TRUE; argv[i].Equal["+word"] => word ¬ TRUE; argv[i].Equal["+def"] => def ¬ TRUE; argv[i].Equal["+all"] => all ¬ TRUE; ENDCASE => with ¬ argv[i]; ENDLOOP; [found, matchStart, matchEnd, selStart, selEnd, subs] ¬ TextFind.RopeSearch[direction, target, subject, 0, subject.Length[], case, word, def, all]; cmd.out.PutFL["Search[%g, \"%q\", \"%q\", %gcase, %gword, %gdef, %gall] => [%g, %g, %g, %g, %g]\n", LIST[ [rope[IF direction=forward THEN "forward" ELSE "backward"]], [rope[argv[1]]], [rope[argv[2]]], B2S[case], B2S[word], B2S[def], B2S[all], [boolean[found]], [integer[matchStart]], [integer[matchEnd]], [integer[selStart]], [integer[selEnd]] ]]; IF with#NIL THEN { ans: ROPE ¬ TextFind.RopeReplace[subject, 0, subject.Length[], with, TRUE, subs]; cmd.out.PutF["Replace[\"%q\"] => \"%q\"\n", [rope[with]], [rope[ans]] ]}; RETURN}}; B2S: PROC [b: BOOL] RETURNS [IO.Value] ~ {RETURN [[character[IF b THEN '+ ELSE '-]]]}; Commander.Register["TestTextFind", TestFind]; MakeDo.AddFinder[finder: [name: "Pattern", finderProc: PatternFind], end: front]; AddPattern["'>sun4_solaris'>.so", LIST["'>sun4_solaris'>.c2c.o"], "ComplexCc -out .so -in .c2c.o -class sun4_solaris -cSwitch \"-G\""]; AddPattern["'>-scc.o", LIST["'>.c"], "! cc -g -c .c -o -scc.o"]; AddPattern["'>-gcc.o", LIST["'>.c"], "! gcc -g -c .c -o -gcc.o"]; AddPattern["'>.nm", LIST["'>.o"], "! nm -ap .o '> .nm"]; AddPattern["'>.dvi", LIST["'>.tex"], "! latex .tex"]; AddPattern["'>.4050ps", LIST["'>.dvi"], "! 4050dvips .dvi '> .4050ps"]; AddPattern["'>.DTps", LIST["'>.dvi"], "! DTdvips .dvi '> .DTps"]; AddPattern["'>.LWps", LIST["'>.dvi"], "! dvips .dvi '> .LWps"]; MakeDo.AddFinder[finder: [name: "MakeIt", finderProc: MakeItFind], end: front]; END. v MakeItDepsImpl.mesa Copyright Ó 1986, 1991, 1993 by Xerox Corporation. All rights reserved. Eric Nickell, August 19, 1986 11:37:10 am PDT Mike Spreitzer June 23, 1986 12:06:51 pm PDT Last tweaked by Mike Spreitzer on May 18, 1993 4:16 pm PDT Willie-s, May 18, 1993 2:54 pm PDT Michael Plass, September 30, 1991 1:20 pm PDT Here, line matches the specified pattern Ê –(cedarcode) style•NewlineDelimiter ™™Icodešœ Ïeœ<™HK™-K™,K™:K™"K™-K™—šÏk ˜ Kšœ žœžœ ˜K˜Kšžœžœ?˜GKšžœ˜Kšœ˜K˜K˜ K˜—K˜KšÐlnœž ˜Kšžœ%žœžœ˜JK˜Kšž˜Icode1•StartOfExpansionØ -- [resultName: ROPE, finderData: REF ANY] RETURNS [found: BOOLEAN, sought: MakeDo.Node, makes: MakeDo.NodeList, cmdFrom: MakeDo.NodeList, from: MakeDo.From, cmd: ROPE, class: MakeDo.ActionClass, foundData: REF ANY]šžœžœžœ˜Lš œ žœžœžœžœ˜Lšœ žœžœžœ ˜(Lšœ žœžœ˜+šœžœžœ˜#L˜L˜Lšœžœ˜—Lšœžœžœ˜3šœžœžœ˜'L˜L˜Lšœžœ˜ —šœ žœžœ˜Lšœ$ž˜(Lšœ˜—šœ#žœ˜@LšÏnœ˜*Lš œ˜Lšœ˜—šœ"žœ˜?Lš œ˜*Lš œ˜L˜—Lšœžœ˜šÏb œžœžœžœžœžœ žœažœ(žœžœÏcœ˜€Lšœ žœ ˜Lšœžœ˜Lšœžœ˜Lšœ žœ˜L˜Lšœžœžœ žœ˜VL˜L˜1L˜šžœ!žœžœž˜3L˜Lšœ(žœ˜,L˜Lšœ‘žœ˜—šžœžœ˜Lšœžœžœ˜šžœ&žœžœž˜8Lšœ žœCžœ˜cL˜TLšœžœ˜.Lšžœ˜—L–D[someName: ROPE, class: MakeDo.NodeClass, mayAdd: BOOL _ TRUE]šœ žœ˜L–D[someName: ROPE, class: MakeDo.NodeClass, mayAdd: BOOL _ TRUE]šœžœI˜ULšœjžœ˜~L˜Lšœ žœ-˜Lšœžœ˜ L–"[name: ROPE, wDir: ROPE _ NIL]šœžœžœYžœ˜L–[stream: STREAM]š žœ/žœžœžœžœžœ˜‚L–'[self: STREAM, abort: BOOL _ FALSE]šžœ˜L™(L–>[s1: ROPE, s2: ROPE, pos1: INT _ 0, case: BOOL _ TRUE]šœH¢˜XL–>[s1: ROPE, s2: ROPE, pos1: INT _ 0, case: BOOL _ TRUE]šœC¢˜UL–)[rope: ROPE, oldStream: STREAM _ NIL]šœžœžœ ˜šž˜L–-[stream: STREAM, breakProc: IO.BreakProc]š œžœžœ žœ$žœ žœžœ)˜L–D[someName: ROPE, class: MakeDo.NodeClass, mayAdd: BOOL _ TRUE]šœžœJ˜^Lšžœ˜—L–'[self: STREAM, abort: BOOL _ FALSE]šžœ˜L–'[self: STREAM, abort: BOOL _ FALSE]šžœ˜#L˜—L–T -- [a: MakeDo.Action, result: MakeDo.Node] RETURNS [consistent: BOOL, reason: ROPE]š  œžœžœ žœžœ˜Lš £œžœ)žœžœ žœ¢œ˜Lšœžœžœ˜šÐnt œžœ5žœ˜QL–[n: MakeDo.Node]šœžœ˜4Lšžœžœžœ˜,Lšœžœ˜Lšžœžœ6žœžœ'žœ žœ<žœj˜¸Lšžœ˜—Lšœ3˜3L–[n: MakeDo.Node]šœ žœ,˜˜hLšœ&žœ<˜f—LšœO˜OK˜Kšžœ˜—…—'Š: