while thorough, it will contain some unintuitive noise:\n #\n # '2015_06_04', in addition to matching 2015_06_04, will also contain\n # 5(!) PASSwORD),\n # the number of ways to lowercase U+L letters with L lowercase letters or less.\n U = (chr for chr in word.split('') when chr.match /[A-Z]/).length\n L = (chr for chr in word.split('') when chr.match /[a-z]/).length\n variations = 0\n variations += @nCk(U + L, i) for i in [1..Math.min(U, L)]\n variations\n\n l33t_variations: (match) ->\n return 1 if not match.l33t\n variations = 1\n for subbed, unsubbed of match.sub\n # lower-case match.token before calculating: capitalization shouldn't affect l33t calc.\n chrs = match.token.toLowerCase().split('')\n S = (chr for chr in chrs when chr == subbed).length # num of subbed chars\n U = (chr for chr in chrs when chr == unsubbed).length # num of unsubbed chars\n if S == 0 or U == 0\n # for this sub, password is either fully subbed (444) or fully unsubbed (aaa)\n # treat that as doubling the space (attacker needs to try fully subbed chars in addition to\n # unsubbed. * Product(m.guesses for m in sequence) + D^(l - 1)\n #\n # where l is the length of the sequence.\n #\n # the factorial term is the number of ways to order l patterns.\n #\n # the D^(l-1) term is another length penalty, roughly capturing the idea that an\n # attacker will try lower-length sequences first before trying length-l sequences.\n #\n # for example, consider a sequence that is date-repeat-dictionary.\n # - an attacker would need to try other date-repeat-dictionary combinations,\n # hence the product term.\n # - an attacker would need to try repeat-date-dictionary, dictionary-repeat-date,\n # , hence the factorial term.\n # - an attacker would also likely try length-1 (dictionary) and length-2 (dictionary-date)\n # sequences before length-3. lamp floor bridgeport crystal designs costco "matching = require './matching'\nscoring = require './scoring'\ntime_estimates = require './time_estimates'\nfeedback = require './feedback'\n\ntime = -> (new Date()).getTime()\n\nzxcvbn = (password, user_inputs = []) ->\n start = time()\n # reset the user inputs matcher on a per-request basis to keep things stateless\n sanitized_inputs = []\n for arg in user_inputs\n if typeof arg in [\"string\", \"number\", \"boolean\"]\n sanitized_inputs.push arg.toString().toLowerCase()\n matching.set_user_input_dictionary sanitized_inputs\n matches = matching.omnimatch password\n result = scoring.most_guessable_match_sequence password, matches\n result.calc_time = time() - start\n attack_times = time_estimates.estimate_attack_times result.guesses\n for prop, val of attack_times\n result[prop] = val\n result.feedback = feedback.get_feedback result.score, result.sequence\n result\n\nmodule.exports = zxcvbn\n", "src/feedback.coffee", Join 69,319 Costco shoppers that receive our latest clearance deals via email. "src/frequency_lists.coffee", #Costco #FrugalHotspot, Martin Furniture Glass Door Lighted Bookcase. "src/scoring.coffee", (We are not affiliated with Costco corporate.). or, if there's more uppercase than lower (for eg. "sourcesContent": [ and display_num != 1\n display_str\n\nmodule.exports = time_estimates\n" the following is a O(l_max * (n + m)) dynamic programming algorithm\n # for a length-n password with m candidate matches. '\n if feedback?\n feedback.suggestions.unshift extra_feedback\n feedback.warning = '' unless feedback.warning?\n else\n feedback =\n warning: ''\n suggestions: [extra_feedback]\n feedback\n\n get_match_feedback: (match, is_sole_match) ->\n switch match.pattern\n when 'dictionary'\n @get_dictionary_match_feedback match, is_sole_match\n\n when 'spatial'\n layout = match.graph.toUpperCase()\n warning = if match.turns == 1\n 'Straight rows of keys are easy to guess'\n else\n 'Short keyboard patterns are easy to guess'\n warning: warning\n suggestions: [\n 'Use a longer keyboard pattern with more turns'\n ]\n\n when 'repeat'\n warning = if match.base_token.length == 1\n 'Repeats like \"aaa\" are easy to guess'\n else\n 'Repeats like \"abcabcabc\" are only slightly harder to guess than \"abc\"'\n warning: warning\n suggestions: [\n 'Avoid repeated words and characters'\n ]\n\n when 'sequence'\n warning: \"Sequences like abc or 6543 are easy to guess\"\n suggestions: [\n 'Avoid sequences'\n ]\n\n when 'regex'\n if match.regex_name == 'recent_year'\n warning: \"Recent years are easy to guess\"\n suggestions: [\n 'Avoid recent years'\n 'Avoid years that are associated with you'\n ]\n\n when 'date'\n warning: \"Dates are often easy to guess\"\n suggestions: [\n 'Avoid dates and years that are associated with you'\n ]\n\n get_dictionary_match_feedback: (match, is_sole_match) ->\n warning = if match.dictionary_name == 'passwords'\n if is_sole_match and not match.l33t and not match.reversed\n if match.rank <= 10\n 'This is a top-10 common password'\n else if match.rank <= 100\n 'This is a top-100 common password'\n else\n 'This is a very common password'\n else if match.guesses_log10 <= 4\n 'This is similar to a commonly used password'\n else if match.dictionary_name == 'english'\n if is_sole_match\n 'A word by itself is easy to guess'\n else if match.dictionary_name in ['surnames', 'male_names', 'female_names']\n if is_sole_match\n 'Names and surnames by themselves are easy to guess'\n else\n 'Common names and surnames are easy to guess'\n else\n ''\n\n suggestions = []\n word = match.token\n if word.match(scoring.START_UPPER)\n suggestions.push \"Capitalization doesn't help very much\"\n else if word.match(scoring.ALL_UPPER) and word.toLowerCase() != word\n suggestions.push \"All-uppercase is almost as easy to guess as all-lowercase\"\n\n if match.reversed and match.token.length >= 4\n suggestions.push \"Reversed words aren't much harder to guess\"\n if match.l33t\n suggestions.push \"Predictable substitutions like '@' instead of 'a' don't help very much\"\n\n result =\n warning: warning\n suggestions: suggestions\n result\n\nmodule.exports = feedback\n", rice brown organic costco ounce bowls '\\' has degree 1.\n# this calculates the average over all keys.\ncalc_average_degree = (graph) ->\n average = 0\n for key, neighbors of graph\n average += (n for n in neighbors when n).length\n average /= (k for k,v of graph).length\n average\n\nBRUTEFORCE_CARDINALITY = 10\nMIN_GUESSES_BEFORE_GROWING_SEQUENCE = 10000\nMIN_SUBMATCH_GUESSES_SINGLE_CHAR = 10\nMIN_SUBMATCH_GUESSES_MULTI_CHAR = 50\n\nscoring =\n nCk: (n, k) ->\n # http://blog.plover.com/math/choose.html\n return 0 if k > n\n return 1 if k == 0\n r = 1\n for d in [1..k]\n r *= n\n r /= d\n n -= 1\n r\n\n log10: (n) -> Math.log(n) / Math.log(10) # IE doesn't support Math.log10 :(\n log2: (n) -> Math.log(n) / Math.log(2)\n\n factorial: (n) ->\n # unoptimized, called only on small n\n return 1 if n < 2\n f = 1\n f *= i for i in [2..n]\n f\n\n # ------------------------------------------------------------------------------\n # search --- most guessable match sequence -------------------------------------\n # ------------------------------------------------------------------------------\n #\n # takes a sequence of overlapping matches, returns the non-overlapping sequence with\n # minimum guesses. assuming at minimum D guesses per pattern type,\n # D^(l-1) approximates Sum(D^i for i in [1..l-1]\n #\n # ------------------------------------------------------------------------------\n\n most_guessable_match_sequence: (password, matches, _exclude_additive=false) ->\n\n n = password.length\n\n # partition matches into sublists according to ending index j\n matches_by_j = ([] for _ in [0n])\n for m in matches\n matches_by_j[m.j].push m\n # small detail: for deterministic output, sort each sublist by i.\n for lst in matches_by_j\n lst.sort (m1, m2) -> m1.i - m2.i\n\n optimal =\n # optimal.m[k][l] holds final match in the best length-l match sequence covering the\n # password prefix up to k, inclusive.\n # if there is no length-l sequence that scores better (fewer guesses) than\n # a shorter match sequence spanning the same prefix, optimal.m[k][l] is undefined.\n m: ({} for _ in [0n])\n\n # same structure as optimal.m -- holds the product term Prod(m.guesses for m in sequence).\n # optimal.pi allows for fast (non-looping) updates to the minimization function.\n pi: ({} for _ in [0n])\n\n # same structure as optimal.m -- holds the overall metric.\n g: ({} for _ in [0n])\n\n # helper: considers whether a length-l sequence ending at match m is better (fewer guesses)\n # than previously encountered sequences, updating state if so.\n update = (m, l) =>\n k = m.j\n pi = @estimate_guesses m, password\n if l > 1\n # we're considering a length-l sequence ending with match m:\n # obtain the product term in the minimization function by multiplying m's guesses\n # by the product of the length-(l-1) sequence ending just before m, at m.i - 1.\n pi *= optimal.pi[m.i - 1][l - 1]\n # calculate the minimization func\n g = @factorial(l) * pi\n unless _exclude_additive\n g += Math.pow(MIN_GUESSES_BEFORE_GROWING_SEQUENCE, l - 1)\n # update state if new best.\n # first see if any competing sequences covering this prefix, with l or fewer matches,\n # fare better than this sequence. Sunvilla Beth Outdoor 4-Piece Deep Seating Set, Agio Portland 6-Piece Woven Outdoor Deep Seating Set, Gilman Creek Sweeney Fabric Power Reclining Sectional, Agio Park Falls 4Pc Woven Deep Seating Outdoor Set, Universal Broadmoor Opal 72 Accent Console, Simon Li Aleena Leather Power Reclining Loveseat, Bayside Furnishings 60 Kitchen Island Console, StriVectin Vitamin C + SPF 30 Moisturizer, First Alert Fire Extinguisher Kitchen 5-B:C, Toms of Maine Silly Strawberry Toothpaste 3-Pack. ]/\n spatial_match_helper: (password, graph, graph_name) ->\n matches = []\n i = 0\n while i < password.length - 1\n j = i + 1\n last_direction = null\n turns = 0\n if graph_name in ['qwerty', 'dvorak'] and @SHIFTED_RX.exec(password.charAt(i))\n # initial character is shifted\n shifted_count = 1\n else\n shifted_count = 0\n loop\n prev_char = password.charAt(j-1)\n found = false\n found_direction = -1\n cur_direction = -1\n adjacents = graph[prev_char] or []\n # consider growing pattern by one character if j hasn't gone over the edge.\n if j < password.length\n cur_char = password.charAt(j)\n for adj in adjacents\n cur_direction += 1\n if adj and adj.indexOf(cur_char) != -1\n found = true\n found_direction = cur_direction\n if adj.indexOf(cur_char) == 1\n # index 1 in the adjacency means the key is shifted,\n # 0 means unshifted: A vs a, % vs 5, etc.\n # for example, 'q' is adjacent to the entry '2@'.\n # @ is shifted w/ index 1, 2 is unshifted.\n shifted_count += 1\n if last_direction != found_direction\n # adding a turn is correct even in the initial case when last_direction is null:\n # every spatial pattern starts with a turn.\n turns += 1\n last_direction = found_direction\n break\n # if the current pattern continued, extend j and try to grow again\n if found\n j += 1\n # otherwise push the pattern discovered so far, if any\n else\n if j - i > 2 # don't consider length 1 or 2 chains.\n matches.push\n pattern: 'spatial'\n i: i\n j: j-1\n token: password[ij]\n graph: graph_name\n turns: turns\n shifted_count: shifted_count\n # and then start a new search for the rest of the password.\n i = j\n break\n matches\n\n #-------------------------------------------------------------------------------\n # repeats (aaa, abcabcabc) and sequences (abcdef) ------------------------------\n #-------------------------------------------------------------------------------\n\n repeat_match: (password) ->\n matches = []\n greedy = /(.+)\\1+/g\n lazy = /(.+? Costco97 is a place to discover and share unadvertised clearance deals found at Costco stores and online. When autocomplete results are available use up and down arrows to review and enter to select. # a match's guess estimate doesn't change. "adjacency_graphs = require('./adjacency_graphs')\n\n# on qwerty, 'g' has degree 6, being adjacent to 'ftyhbv'. "sourceRoot": "", #Costco #FrugalHotspot, Imagio Home Gentlemans Chest. "(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o\", null, null], \"-\": [\"0)\", null, null, \"=+\", \"[{\", \"pP\"], \".\": [\",\", \";:\", \"'\\\"\", null, null, null], \"0\": [\"9(\", null, null, \"-_\", \"pP\", \"oO\"], \"1\": [\"`~\", null, null, \"2@\", \"qQ\", null], \"2\": [\"1!\", null, null, \"3#\", \"wW\", \"qQ\"], \"3\": [\"2@\", null, null, \"4$\", \"eE\", \"wW\"], \"4\": [\"3#\", null, null, \"5%\", \"rR\", \"eE\"], \"5\": [\"4$\", null, null, \"6^\", \"tT\", \"rR\"], \"6\": [\"5%\", null, null, \"7&\", \"yY\", \"tT\"], \"7\": [\"6^\", null, null, \"8*\", \"uU\", \"yY\"], \"8\": [\"7&\", null, null, \"9(\", \"iI\", \"uU\"], \"9\": [\"8*\", null, null, \"0)\", \"oO\", \"iI\"], \":\": [\"lL\", \"pP\", \"[{\", \"'\\\"\", \"/?\", \".>\"], \";\": [\"lL\", \"pP\", \"[{\", \"'\\\"\", \"/?\", \".>\"], \"\", null, null], \"=\": [\"-_\", null, null, null, \"]}\", \"[{\"], \">\": [\",\", \";:\", \"'\\\"\", null, null, null], \"@\": [\"1!\", null, null, \"3#\", \"wW\", \"qQ\"], \"A\": [null, \"qQ\", \"wW\", \"sS\", \"zZ\", null], \"B\": [\"vV\", \"gG\", \"hH\", \"nN\", null, null], \"C\": [\"xX\", \"dD\", \"fF\", \"vV\", null, null], \"D\": [\"sS\", \"eE\", \"rR\", \"fF\", \"cC\", \"xX\"], \"E\": [\"wW\", \"3#\", \"4$\", \"rR\", \"dD\", \"sS\"], \"F\": [\"dD\", \"rR\", \"tT\", \"gG\", \"vV\", \"cC\"], \"G\": [\"fF\", \"tT\", \"yY\", \"hH\", \"bB\", \"vV\"], \"H\": [\"gG\", \"yY\", \"uU\", \"jJ\", \"nN\", \"bB\"], \"I\": [\"uU\", \"8*\", \"9(\", \"oO\", \"kK\", \"jJ\"], \"J\": [\"hH\", \"uU\", \"iI\", \"kK\", \"mM\", \"nN\"], \"K\": [\"jJ\", \"iI\", \"oO\", \"lL\", \",\", \",\", \",\", \",\"], \"%\": [\"4$\", null, null, \"6^\", \"yY\", \"pP\"], \"&\": [\"6^\", null, null, \"8*\", \"gG\", \"fF\"], \"'\": [null, \"1!\", \"2@\", \",\", \"oO\", \"aA\"], \"-\": [\"sS\", \"/?\", \"=+\", null, null, \"zZ\"], \".\": [\",\", \",\"], \"5\": [\"4$\", null, null, \"6^\", \"yY\", \"pP\"], \"6\": [\"5%\", null, null, \"7&\", \"fF\", \"yY\"], \"7\": [\"6^\", null, null, \"8*\", \"gG\", \"fF\"], \"8\": [\"7&\", null, null, \"9(\", \"cC\", \"gG\"], \"9\": [\"8*\", null, null, \"0)\", \"rR\", \"cC\"], \":\": [null, \"aA\", \"oO\", \"qQ\", null, null], \";\": [null, \"aA\", \"oO\", \"qQ\", null, null], \"\", \"oO\", \"aA\"], \"=\": [\"/?\", \"]}\", null, \"\\\\|\", null, \"-_\"], \">\": [\",\", \"pP\", \"uU\", \"jJ\", \"qQ\"], \"F\": [\"yY\", \"6^\", \"7&\", \"gG\", \"dD\", \"iI\"], \"G\": [\"fF\", \"7&\", \"8*\", \"cC\", \"hH\", \"dD\"], \"H\": [\"dD\", \"gG\", \"cC\", \"tT\", \"mM\", \"bB\"], \"I\": [\"uU\", \"yY\", \"fF\", \"dD\", \"xX\", \"kK\"], \"J\": [\"qQ\", \"eE\", \"uU\", \"kK\", null, null], \"K\": [\"jJ\", \"uU\", \"iI\", \"xX\", null, null], \"L\": [\"rR\", \"0)\", \"[{\", \"/?\", \"sS\", \"nN\"], \"M\": [\"bB\", \"hH\", \"tT\", \"wW\", null, null], \"N\": [\"tT\", \"rR\", \"lL\", \"sS\", \"vV\", \"wW\"], \"O\": [\"aA\", \",\", \"eE\", \"qQ\", \";:\"], \"P\": [\".>\", \"4$\", \"5%\", \"yY\", \"uU\", \"eE\"], \"Q\": [\";:\", \"oO\", \"eE\", \"jJ\", null, null], \"R\": [\"cC\", \"9(\", \"0)\", \"lL\", \"nN\", \"tT\"], \"S\": [\"nN\", \"lL\", \"/?\", \"-_\", \"zZ\", \"vV\"], \"T\": [\"hH\", \"cC\", \"rR\", \"nN\", \"wW\", \"mM\"], \"U\": [\"eE\", \"pP\", \"yY\", \"iI\", \"kK\", \"jJ\"], \"V\": [\"wW\", \"nN\", \"sS\", \"zZ\", null, null], \"W\": [\"mM\", \"tT\", \"nN\", \"vV\", null, null], \"X\": [\"kK\", \"iI\", \"dD\", \"bB\", null, null], \"Y\": [\"pP\", \"5%\", \"6^\", \"fF\", \"iI\", \"uU\"], \"Z\": [\"vV\", \"sS\", \"-_\", null, null, null], \"[\": [\"0)\", null, null, \"]}\", \"/?\", \"lL\"], \"\\\\\": [\"=+\", null, null, null, null, null], \"]\": [\"[{\", null, null, null, \"=+\", \"/?\"], \"^\": [\"5%\", null, null, \"7&\", \"fF\", \"yY\"], \"_\": [\"sS\", \"/?\", \"=+\", null, null, \"zZ\"], \"`\": [null, null, null, \"1!\", null, null], \"a\": [null, \"'\\\"\", \",\", \"pP\", \"uU\", \"jJ\", \"qQ\"], \"f\": [\"yY\", \"6^\", \"7&\", \"gG\", \"dD\", \"iI\"], \"g\": [\"fF\", \"7&\", \"8*\", \"cC\", \"hH\", \"dD\"], \"h\": [\"dD\", \"gG\", \"cC\", \"tT\", \"mM\", \"bB\"], \"i\": [\"uU\", \"yY\", \"fF\", \"dD\", \"xX\", \"kK\"], \"j\": [\"qQ\", \"eE\", \"uU\", \"kK\", null, null], \"k\": [\"jJ\", \"uU\", \"iI\", \"xX\", null, null], \"l\": [\"rR\", \"0)\", \"[{\", \"/?\", \"sS\", \"nN\"], \"m\": [\"bB\", \"hH\", \"tT\", \"wW\", null, null], \"n\": [\"tT\", \"rR\", \"lL\", \"sS\", \"vV\", \"wW\"], \"o\": [\"aA\", \",\", \"eE\", \"qQ\", \";:\"], \"p\": [\".>\", \"4$\", \"5%\", \"yY\", \"uU\", \"eE\"], \"q\": [\";:\", \"oO\", \"eE\", \"jJ\", null, null], \"r\": [\"cC\", \"9(\", \"0)\", \"lL\", \"nN\", \"tT\"], \"s\": [\"nN\", \"lL\", \"/?\", \"-_\", \"zZ\", \"vV\"], \"t\": [\"hH\", \"cC\", \"rR\", \"nN\", \"wW\", \"mM\"], \"u\": [\"eE\", \"pP\", \"yY\", \"iI\", \"kK\", \"jJ\"], \"v\": [\"wW\", \"nN\", \"sS\", \"zZ\", null, null], \"w\": [\"mM\", \"tT\", \"nN\", \"vV\", null, null], \"x\": [\"kK\", \"iI\", \"dD\", \"bB\", null, null], \"y\": [\"pP\", \"5%\", \"6^\", \"fF\", \"iI\", \"uU\"], \"z\": [\"vV\", \"sS\", \"-_\", null, null, null], \"{\": [\"0)\", null, null, \"]}\", \"/?\", \"lL\"], \"|\": [\"=+\", null, null, null, null, null], \"}\": [\"[{\", null, null, null, \"=+\", \"/?\"], \"~\": [null, null, null, \"1!\", null, null]}\n keypad: {\"*\": [\"/\", null, null, null, \"-\", \"+\", \"9\", \"8\"], \"+\": [\"9\", \"*\", \"-\", null, null, null, null, \"6\"], \"-\": [\"*\", null, null, null, null, null, \"+\", \"9\"], \".\": [\"0\", \"2\", \"3\", null, null, null, null, null], \"/\": [null, null, null, null, \"*\", \"9\", \"8\", \"7\"], \"0\": [null, \"1\", \"2\", \"3\", \".\", null, null, null], \"1\": [null, null, \"4\", \"5\", \"2\", \"0\", null, null], \"2\": [\"1\", \"4\", \"5\", \"6\", \"3\", \".\", \"0\", null], \"3\": [\"2\", \"5\", \"6\", null, null, null, \".\", \"0\"], \"4\": [null, null, \"7\", \"8\", \"5\", \"2\", \"1\", null], \"5\": [\"4\", \"7\", \"8\", \"9\", \"6\", \"3\", \"2\", \"1\"], \"6\": [\"5\", \"8\", \"9\", \"+\", null, null, \"3\", \"2\"], \"7\": [null, null, null, \"/\", \"8\", \"5\", \"4\", null], \"8\": [\"7\", null, \"/\", \"*\", \"9\", \"6\", \"5\", \"4\"], \"9\": [\"8\", \"/\", \"*\", \"-\", \"+\", null, \"6\", \"5\"]}\n mac_keypad: {\"*\": [\"/\", null, null, null, null, null, \"-\", \"9\"], \"+\": [\"6\", \"9\", \"-\", null, null, null, null, \"3\"], \"-\": [\"9\", \"/\", \"*\", null, null, null, \"+\", \"6\"], \".\": [\"0\", \"2\", \"3\", null, null, null, null, null], \"/\": [\"=\", null, null, null, \"*\", \"-\", \"9\", \"8\"], \"0\": [null, \"1\", \"2\", \"3\", \".\", null, null, null], \"1\": [null, null, \"4\", \"5\", \"2\", \"0\", null, null], \"2\": [\"1\", \"4\", \"5\", \"6\", \"3\", \".\", \"0\", null], \"3\": [\"2\", \"5\", \"6\", \"+\", null, null, \".\", \"0\"], \"4\": [null, null, \"7\", \"8\", \"5\", \"2\", \"1\", null], \"5\": [\"4\", \"7\", \"8\", \"9\", \"6\", \"3\", \"2\", \"1\"], \"6\": [\"5\", \"8\", \"9\", \"-\", \"+\", null, \"3\", \"2\"], \"7\": [null, null, null, \"=\", \"8\", \"5\", \"4\", null], \"8\": [\"7\", null, \"=\", \"/\", \"9\", \"6\", \"5\", \"4\"], \"9\": [\"8\", \"=\", \"/\", \"*\", \"-\", \"+\", \"6\", \"5\"], \"=\": [null, null, null, null, \"/\", \"9\", \"8\", \"7\"]}\n\nmodule.exports = adjacency_graphs\n", "file": "generated.js", #Costco #FrugalHotspot, Bayside Furnishings Ladder Bookcase. costco 2pk "time_estimates =\n estimate_attack_times: (guesses) ->\n crack_times_seconds =\n online_throttling_100_per_hour: guesses / (100 / 3600)\n online_no_throttling_10_per_second: guesses / 10\n offline_slow_hashing_1e4_per_second: guesses / 1e4\n offline_fast_hashing_1e10_per_second: guesses / 1e10\n\n crack_times_display = {}\n for scenario, seconds of crack_times_seconds\n crack_times_display[scenario] = @display_time seconds\n\n crack_times_seconds: crack_times_seconds\n crack_times_display: crack_times_display\n score: @guesses_to_score guesses\n\n\n guesses_to_score: (guesses) ->\n DELTA = 5\n if guesses < 1e3 + DELTA\n # risky password: \"too guessable\"\n 0\n else if guesses < 1e6 + DELTA\n # modest protection from throttled online attacks: \"very guessable\"\n 1\n else if guesses < 1e8 + DELTA\n # modest protection from unthrottled online attacks: \"somewhat guessable\"\n 2\n else if guesses < 1e10 + DELTA\n # modest protection from offline attacks: \"safely unguessable\"\n # assuming a salted, slow hash function like bcrypt, scrypt, PBKDF2, argon, etc\n 3\n else\n # strong protection from offline attacks under same scenario: \"very unguessable\"\n 4\n\n display_time: (seconds) ->\n minute = 60\n hour = minute * 60\n day = hour * 24\n month = day * 31\n year = month * 12\n century = year * 100\n [display_num, display_str] = if seconds < 1\n [null, 'less than a second']\n else if seconds < minute\n base = Math.round seconds\n [base, \"#{base} second\"]\n else if seconds < hour\n base = Math.round seconds / minute\n [base, \"#{base} minute\"]\n else if seconds < day\n base = Math.round seconds / hour\n [base, \"#{base} hour\"]\n else if seconds < month\n base = Math.round seconds / day\n [base, \"#{base} day\"]\n else if seconds < year\n base = Math.round seconds / month\n [base, \"#{base} month\"]\n else if seconds < century\n base = Math.round seconds / year\n [base, \"#{base} year\"]\n else\n [null, 'centuries']\n display_str += 's' if display_num?

Sitemap 9