sed '/Target/s/\(#Gi[0-9]*_[0-9]*:\)/ifInErrors\1\&ifInErrors\1/' input.txt
sed '/Target/ is equivalent to
grep Target | sed, except it involves one less process & one less pipe.
s/ means 'substitution', the most common sed command;
s/foo/bar/ would replace instances of the string foo with bar, for example.
/\(#Gi[0-9]*\/[0-9]*:\) ... the brackets (which need to be escaped with a
\) tell sed to mark everything between them as
\1 (or \2 for the second marked pattern, \3 for the third etc).
[0-9]* means 'any number of numbers', and
\/ is an escaped
/ (it needs to be escaped because I'm using
/ as the separator for sed; if you use another separator, like
|, then you wouldn't need to escape the /). So
#Gi[0-9]*\/[0-9]*: is a pattern meaning 'start with #, followed by Gi, then any number of numbers, then /, then any number of numbers, ending with :'.
\1 matches whatever string is detected by the pattern
#Gi[0-9]*\/[0-9]*: In the first string given in the question,
## The pattern #Gi[0-9]*\/[0-9]*: will match the substring
/ifInErrors\1\&ifInErrors\1/ tells sed 'replace
Some extra stuff: if you wanted to just print the lines that begin with 'Target', doing the sed substitution, you could use this line:
sed -n '/Target/s/\(#Gi[0-9]*\/[0-9]*:\)/ifInErrors\1\&ifInErrors\1/p'
-n tells sed 'don't print the output', and the
p at the end tells it to print the lines sed is working on.
If you wanted to over-write your original file, you would use this:
sed -i '/Target/s/\(#Gi[0-9]*\/[0-9]*:\)/ifInErrors\1\&ifInErrors\1/'