| 1 | import * as v6 from './constants';
|
|---|
| 2 |
|
|---|
| 3 | export function groupPossibilities(possibilities: string[]): string {
|
|---|
| 4 | return `(${possibilities.join('|')})`;
|
|---|
| 5 | }
|
|---|
| 6 |
|
|---|
| 7 | export function padGroup(group: string): string {
|
|---|
| 8 | if (group.length < 4) {
|
|---|
| 9 | return `0{0,${4 - group.length}}${group}`;
|
|---|
| 10 | }
|
|---|
| 11 |
|
|---|
| 12 | return group;
|
|---|
| 13 | }
|
|---|
| 14 |
|
|---|
| 15 | export const ADDRESS_BOUNDARY = '[^A-Fa-f0-9:]';
|
|---|
| 16 |
|
|---|
| 17 | export function simpleRegularExpression(groups: string[]) {
|
|---|
| 18 | const zeroIndexes: number[] = [];
|
|---|
| 19 |
|
|---|
| 20 | groups.forEach((group, i) => {
|
|---|
| 21 | const groupInteger = parseInt(group, 16);
|
|---|
| 22 |
|
|---|
| 23 | if (groupInteger === 0) {
|
|---|
| 24 | zeroIndexes.push(i);
|
|---|
| 25 | }
|
|---|
| 26 | });
|
|---|
| 27 |
|
|---|
| 28 | // You can technically elide a single 0, this creates the regular expressions
|
|---|
| 29 | // to match that eventuality
|
|---|
| 30 | const possibilities = zeroIndexes.map((zeroIndex) =>
|
|---|
| 31 | groups
|
|---|
| 32 | .map((group, i) => {
|
|---|
| 33 | if (i === zeroIndex) {
|
|---|
| 34 | const elision = i === 0 || i === v6.GROUPS - 1 ? ':' : '';
|
|---|
| 35 |
|
|---|
| 36 | return groupPossibilities([padGroup(group), elision]);
|
|---|
| 37 | }
|
|---|
| 38 |
|
|---|
| 39 | return padGroup(group);
|
|---|
| 40 | })
|
|---|
| 41 | .join(':'),
|
|---|
| 42 | );
|
|---|
| 43 |
|
|---|
| 44 | // The simplest case
|
|---|
| 45 | possibilities.push(groups.map(padGroup).join(':'));
|
|---|
| 46 |
|
|---|
| 47 | return groupPossibilities(possibilities);
|
|---|
| 48 | }
|
|---|
| 49 |
|
|---|
| 50 | export function possibleElisions(
|
|---|
| 51 | elidedGroups: number,
|
|---|
| 52 | moreLeft?: boolean,
|
|---|
| 53 | moreRight?: boolean,
|
|---|
| 54 | ): string {
|
|---|
| 55 | const left = moreLeft ? '' : ':';
|
|---|
| 56 | const right = moreRight ? '' : ':';
|
|---|
| 57 |
|
|---|
| 58 | const possibilities = [];
|
|---|
| 59 |
|
|---|
| 60 | // 1. elision of everything (::)
|
|---|
| 61 | if (!moreLeft && !moreRight) {
|
|---|
| 62 | possibilities.push('::');
|
|---|
| 63 | }
|
|---|
| 64 |
|
|---|
| 65 | // 2. complete elision of the middle
|
|---|
| 66 | if (moreLeft && moreRight) {
|
|---|
| 67 | possibilities.push('');
|
|---|
| 68 | }
|
|---|
| 69 |
|
|---|
| 70 | if ((moreRight && !moreLeft) || (!moreRight && moreLeft)) {
|
|---|
| 71 | // 3. complete elision of one side
|
|---|
| 72 | possibilities.push(':');
|
|---|
| 73 | }
|
|---|
| 74 |
|
|---|
| 75 | // 4. elision from the left side
|
|---|
| 76 | possibilities.push(`${left}(:0{1,4}){1,${elidedGroups - 1}}`);
|
|---|
| 77 |
|
|---|
| 78 | // 5. elision from the right side
|
|---|
| 79 | possibilities.push(`(0{1,4}:){1,${elidedGroups - 1}}${right}`);
|
|---|
| 80 |
|
|---|
| 81 | // 6. no elision
|
|---|
| 82 | possibilities.push(`(0{1,4}:){${elidedGroups - 1}}0{1,4}`);
|
|---|
| 83 |
|
|---|
| 84 | // 7. elision (including sloppy elision) from the middle
|
|---|
| 85 | for (let groups = 1; groups < elidedGroups - 1; groups++) {
|
|---|
| 86 | for (let position = 1; position < elidedGroups - groups; position++) {
|
|---|
| 87 | possibilities.push(
|
|---|
| 88 | `(0{1,4}:){${position}}:(0{1,4}:){${elidedGroups - position - groups - 1}}0{1,4}`,
|
|---|
| 89 | );
|
|---|
| 90 | }
|
|---|
| 91 | }
|
|---|
| 92 |
|
|---|
| 93 | return groupPossibilities(possibilities);
|
|---|
| 94 | }
|
|---|